@@ -864,28 +864,45 @@ and get_written e = match E.written_of e with
864864(* Compute rfmap for registers *)
865865(* ******************************)
866866
867- let map_loc_find loc m =
868- try U.LocEnv. find loc m
869- with Not_found -> []
867+ let map_loc_find loc m = U.LocEnv. safe_find [] loc m
868+
869+ (* Event set ordered by to (generalised) program order *)
870+
871+ module
872+ EvtSetByPo
873+ (I :sig val es : S.event_structure end ) =
874+ struct
875+
876+ let is_before_strict = U. is_before_strict I. es
877+
878+ include Set. Make
879+ (struct
880+
881+ type t = E .event
882+
883+ let compare e1 e2 =
884+ if is_before_strict e1 e2 then - 1
885+ else if is_before_strict e2 e1 then 1
886+ else
887+ let () =
888+ Printf. eprintf " Not ordered stores %a and %a\n " E. debug_event e1
889+ E. debug_event e2
890+ in
891+ assert false
892+
893+ end )
894+
895+ let find_last_before set e =
896+ find_last_opt (fun e' -> is_before_strict e' e) set
897+
898+ let find_first_after e set =
899+ find_first_opt (fun e' -> is_before_strict e e') set
900+
901+ end
870902
871903let match_reg_events add_eq es csn =
872904 let loc_loads_stores = U. collect_reg_loads_stores es in
873- let is_before_strict = U. is_before_strict es in
874- let compare e1 e2 =
875- if is_before_strict e1 e2 then - 1
876- else if is_before_strict e2 e1 then 1
877- else
878- let () =
879- Printf. eprintf " Not ordered stores %a and %a\n " E. debug_event e1
880- E. debug_event e2
881- in
882- assert false
883- in
884- let module StoreSet = Set. Make (struct
885- type t = E .event
886-
887- let compare = compare
888- end ) in
905+ let module StoreSet = EvtSetByPo (struct let es = es end ) in
889906 let add wt rf (rfm , csn ) = (S.RFMap. add wt rf rfm, add_eq rfm wt rf csn) in
890907 (* For all loads find the right store, the one "just before" the load *)
891908 U.LocEnv. fold
@@ -901,9 +918,7 @@ let match_reg_events add_eq es csn =
901918 (* Add the corresponding store for each load *)
902919 List. fold_left
903920 (fun k load ->
904- let f e = is_before_strict e load in
905- let rf =
906- match StoreSet. find_last_opt f stores with
921+ let rf = match StoreSet. find_last_before stores load with
907922 | Some store -> S. Store store
908923 | None -> S. Init
909924 in
@@ -1804,37 +1819,51 @@ let get_rf_value test read =
18041819(* Reconstruct load/store atomic pairs *)
18051820
18061821 let make_atomic_load_store es =
1807- let all = E. atomics_of es.E. events in
1808- let atms = U. collect_atomics es in
1809- U.LocEnv. fold
1810- (fun _loc atms k ->
1811- let atms =
1812- List. filter
1813- (fun e -> not (E. is_load e && E. is_store e))
1814- atms in (* get rid of C RMW *)
1815- let rs,ws = List. partition E. is_load atms in
1816- List. fold_left
1817- (fun k r ->
1818- let exp = E. is_explicit r in
1819- List. fold_left
1820- (fun k w ->
1821- if
1822- S. atomic_pair_allowed r w &&
1823- U. is_before_strict es r w &&
1824- E. is_explicit w = exp &&
1825- not
1826- (E.EventSet. exists
1827- (fun e ->
1828- E. is_explicit e = exp &&
1829- U. is_before_strict es r e &&
1830- U. is_before_strict es e w)
1831- all)
1832- then E.EventRel. add (r,w) k
1833- else k)
1834- k ws)
1835- k rs)
1836- atms E.EventRel. empty
1837-
1822+ let atms,spurious = U. collect_atomics es in
1823+ let module StoreSet = EvtSetByPo (struct let es = es end ) in
1824+ let make_atomic_pairs es k =
1825+ let rs,ws = List. partition E. is_load es in
1826+ let ws = StoreSet. of_list ws
1827+ and intervening_read er ew =
1828+ List. exists
1829+ (fun e ->
1830+ StoreSet. is_before_strict er e
1831+ && StoreSet. is_before_strict e ew)
1832+ rs in
1833+ List. fold_left
1834+ (fun k er ->
1835+ match StoreSet. find_first_after er ws with
1836+ | Some ew ->
1837+ if
1838+ S. atomic_pair_allowed er ew
1839+ && not (intervening_read er ew)
1840+ then
1841+ E.EventRel. add (er,ew) k
1842+ else k
1843+ | None -> k)
1844+ k rs in
1845+ let r1 =
1846+ List. map
1847+ (fun (_ ,m ) ->
1848+ U.LocEnv. fold
1849+ (fun _loc es k ->
1850+ let exps,nexps = List. partition E. is_explicit es in
1851+ make_atomic_pairs exps @@ make_atomic_pairs nexps k)
1852+ m E.EventRel. empty)
1853+ atms |> E.EventRel. unions
1854+ and r2 =
1855+ let iico = es.E. intra_causality_data in
1856+ List. map
1857+ (fun e ->
1858+ if E. is_load e then
1859+ match
1860+ E.EventRel. succs iico e |> E.EventSet. as_singleton
1861+ with
1862+ | None -> assert false (* spurious updates are by pairs *)
1863+ | Some w -> E.EventRel. singleton (e,w)
1864+ else E.EventRel. empty)
1865+ spurious |> E.EventRel. unions in
1866+ E.EventRel. union r1 r2
18381867
18391868(* Retrieve last store from rfmap *)
18401869 let get_max_store _test _es rfm loc =
@@ -1929,12 +1958,9 @@ let get_rf_value test read =
19291958 if C. debug.Debug_herd. mem then begin
19301959 eprintf " Observed locs: {%s}\n " (pp_locations observed_locs)
19311960 end ;
1932- U.LocEnv. fold
1933- (fun loc ws k ->
1934- if keep_observed_loc loc observed_locs then
1935- U.LocEnv. add loc ws k
1936- else k)
1937- loc_stores U.LocEnv. empty
1961+ U.LocEnv. filter
1962+ (fun loc _ -> keep_observed_loc loc observed_locs)
1963+ loc_stores
19381964 else loc_stores in
19391965
19401966 let possible_finals =
0 commit comments