7 |
7 |
8 signature SYNCHRONIZED = |
8 signature SYNCHRONIZED = |
9 sig |
9 sig |
10 type 'a var |
10 type 'a var |
11 val var: string -> 'a -> 'a var |
11 val var: string -> 'a -> 'a var |
12 val guarded_change: ('a -> bool) -> ('a -> Time.time option) -> |
12 val value: 'a var -> 'a |
13 'a var -> (bool -> 'a -> 'b * 'a) -> 'b |
13 val timed_access: 'a var -> ('a -> Time.time option) -> ('a -> ('b * 'a) option) -> 'b option |
|
14 val guarded_access: 'a var -> ('a -> ('b * 'a) option) -> 'b |
14 val change_result: 'a var -> ('a -> 'b * 'a) -> 'b |
15 val change_result: 'a var -> ('a -> 'b * 'a) -> 'b |
15 val change: 'a var -> ('a -> 'a) -> unit |
16 val change: 'a var -> ('a -> 'a) -> unit |
16 end; |
17 end; |
17 |
18 |
18 structure Synchronized: SYNCHRONIZED = |
19 structure Synchronized: SYNCHRONIZED = |
30 {name = name, |
31 {name = name, |
31 lock = Mutex.mutex (), |
32 lock = Mutex.mutex (), |
32 cond = ConditionVar.conditionVar (), |
33 cond = ConditionVar.conditionVar (), |
33 var = ref x}; |
34 var = ref x}; |
34 |
35 |
|
36 fun value (Var {name, lock, cond, var}) = SimpleThread.synchronized name lock (fn () => ! var); |
|
37 |
35 |
38 |
36 (* synchronized access *) |
39 (* synchronized access *) |
37 |
40 |
38 fun guarded_change guard time_limit (Var {name, lock, cond, var}) f = |
41 fun timed_access (Var {name, lock, cond, var}) time_limit f = |
39 SimpleThread.synchronized name lock (fn () => |
42 SimpleThread.synchronized name lock (fn () => |
40 let |
43 let |
41 fun check () = guard (! var) orelse |
44 fun try_change () = |
42 (case time_limit (! var) of |
45 let val x = ! var in |
43 NONE => (ConditionVar.wait (cond, lock); check ()) |
46 (case f x of |
44 | SOME t => ConditionVar.waitUntil (cond, lock, t) andalso check ()); |
47 SOME (y, x') => (var := x'; SOME y) |
45 val ok = check (); |
48 | NONE => |
46 val res = change_result var (f ok); |
49 (case time_limit x of |
|
50 NONE => (ConditionVar.wait (cond, lock); try_change ()) |
|
51 | SOME t => |
|
52 if ConditionVar.waitUntil (cond, lock, t) then try_change () |
|
53 else NONE)) |
|
54 end; |
|
55 val res = try_change (); |
47 val _ = ConditionVar.broadcast cond; |
56 val _ = ConditionVar.broadcast cond; |
48 in res end); |
57 in res end); |
49 |
58 |
50 fun change_result var f = guarded_change (K true) (K NONE) var (K f); |
59 fun guarded_access var f = the (timed_access var (K NONE) f); |
|
60 |
|
61 |
|
62 (* unconditional change *) |
|
63 |
|
64 fun change_result var f = guarded_access var (SOME o f); |
51 fun change var f = change_result var (fn x => ((), f x)); |
65 fun change var f = change_result var (fn x => ((), f x)); |
52 |
66 |
53 end; |
67 end; |