]> xenbits.xensource.com Git - xen.git/commitdiff
tools/oxenstored: Reject invalid watch paths early
authorEdwin Török <edvin.torok@citrix.com>
Fri, 15 Jan 2021 19:28:37 +0000 (19:28 +0000)
committerIan Jackson <iwj@xenproject.org>
Fri, 19 Mar 2021 13:46:25 +0000 (13:46 +0000)
Watches on invalid paths were accepted, but they would never trigger.  The
client also got no notification that its watch is bad and would never trigger.

Found again by the structured fuzzer, due to an error on live update reload:
the invalid watch paths would get rejected during live update and the list of
watches would be different pre/post live update.

The testcase is watch on `//`, which is an invalid path.

Signed-off-by: Edwin Török <edvin.torok@citrix.com>
Acked-by: Christian Lindig <christian.lindig@citrix.com>
Release-Acked-by: Ian Jackson <iwj@xenproject.org>
(cherry picked from commit dc8caf214fb882546b0e93317b9828247a7c9da8)

tools/ocaml/xenstored/connection.ml
tools/ocaml/xenstored/connections.ml

index 0d4dcda7717fe61f30d5a307047d6747c6f21163..daf40994732d2de42818b4bddcdd773abdbeb529 100644 (file)
@@ -158,18 +158,17 @@ let get_children_watches con path =
 let is_dom0 con =
        Perms.Connection.is_dom0 (get_perm con)
 
-let add_watch con path token =
+let add_watch con (path, apath) token =
        if !Quota.activate && !Define.maxwatch > 0 &&
           not (is_dom0 con) && con.nb_watches > !Define.maxwatch then
                raise Quota.Limit_reached;
-       let apath = get_watch_path con path in
        let l = get_watches con apath in
        if List.exists (fun w -> w.token = token) l then
                raise Define.Already_exist;
        let watch = watch_create ~con ~token ~path in
        Hashtbl.replace con.watches apath (watch :: l);
        con.nb_watches <- con.nb_watches + 1;
-       apath, watch
+       watch
 
 let del_watch con path token =
        let apath = get_watch_path con path in
index 4e69de1d42594bd920f55a4dbd9a22aa54c03f77..04840b0680fbb19f17d2b9c26f3b550ab31c43d9 100644 (file)
@@ -114,8 +114,10 @@ let key_of_path path =
        "" :: Store.Path.to_string_list path
 
 let add_watch cons con path token =
-       let apath, watch = Connection.add_watch con path token in
+       let apath = Connection.get_watch_path con path in
+       (* fail on invalid paths early by calling key_of_str before adding watch *)
        let key = key_of_str apath in
+       let watch = Connection.add_watch con (path, apath) token in
        let watches =
                if Trie.mem cons.watches key
                then Trie.find cons.watches key