mirror of
https://github.com/ocaml-multicore/eio.git
synced 2025-06-24 00:01:27 -04:00
Compare commits
49 Commits
Author | SHA1 | Date | |
---|---|---|---|
|
8f7f82d2c1 | ||
|
d3cb04a67e | ||
|
c78db1a757 | ||
|
4a19b2eea9 | ||
|
fdd2593e33 | ||
|
c39449a631 | ||
|
f195295e3d | ||
|
17665689f5 | ||
|
f26d70d642 | ||
|
730033c0f1 | ||
|
cc0274dd2f | ||
|
b971fa1cca | ||
|
2d9e24a67f | ||
|
ae0eaa2dfd | ||
|
681400c18e | ||
|
b41d4d8a49 | ||
|
9b939abedd | ||
|
61f738df51 | ||
|
eb8fe3ef82 | ||
|
debe35621e | ||
|
dd13303a4a | ||
|
216ccff845 | ||
|
a65fd2e612 | ||
|
f8c9441852 | ||
|
8364428147 | ||
|
d2a3e21bc4 | ||
|
424f5e8c96 | ||
|
89019ddd3d | ||
|
534f89cf0e | ||
|
9ca440ac5c | ||
|
e2dc1d79e5 | ||
|
0c414327d1 | ||
|
0f6b65dea2 | ||
|
cc2cd3da32 | ||
|
d47b5e29f7 | ||
|
c2d314b930 | ||
|
33d4e01a30 | ||
|
c45978252a | ||
|
37840760b1 | ||
|
8cb86a703e | ||
|
12721820e4 | ||
|
32e501a198 | ||
|
a21b507de8 | ||
|
54df8fdd62 | ||
|
2cd09925d0 | ||
|
642bdbef7e | ||
|
574afc103a | ||
|
17562f24fe | ||
|
8ef76f06bf |
5
.github/workflows/main.yml
vendored
5
.github/workflows/main.yml
vendored
@ -12,7 +12,7 @@ jobs:
|
|||||||
os:
|
os:
|
||||||
- macos-latest
|
- macos-latest
|
||||||
ocaml-compiler:
|
ocaml-compiler:
|
||||||
- 5.1.x
|
- 5.2.x
|
||||||
local-packages:
|
local-packages:
|
||||||
- eio eio_posix eio_main
|
- eio eio_posix eio_main
|
||||||
|
|
||||||
@ -44,7 +44,7 @@ jobs:
|
|||||||
with:
|
with:
|
||||||
opam-pin: false
|
opam-pin: false
|
||||||
opam-depext: false
|
opam-depext: false
|
||||||
ocaml-compiler: ocaml.5.1.0,ocaml-option-mingw
|
ocaml-compiler: ocaml.5.2.0,ocaml-option-mingw
|
||||||
opam-repositories: |
|
opam-repositories: |
|
||||||
dra27: https://github.com/dra27/opam-repository.git#windows-5.0
|
dra27: https://github.com/dra27/opam-repository.git#windows-5.0
|
||||||
normal: https://github.com/ocaml/opam-repository.git
|
normal: https://github.com/ocaml/opam-repository.git
|
||||||
@ -57,6 +57,7 @@ jobs:
|
|||||||
- run: opam exec -- dune build
|
- run: opam exec -- dune build
|
||||||
- run: opam exec -- dune runtest
|
- run: opam exec -- dune runtest
|
||||||
- run: opam exec -- dune exec -- ./examples/net/main.exe
|
- run: opam exec -- dune exec -- ./examples/net/main.exe
|
||||||
|
- run: opam exec -- dune exec -- ./examples/fs/main.exe
|
||||||
docker:
|
docker:
|
||||||
runs-on: ubuntu-latest
|
runs-on: ubuntu-latest
|
||||||
steps:
|
steps:
|
||||||
|
57
CHANGES.md
57
CHANGES.md
@ -1,3 +1,60 @@
|
|||||||
|
## v1.2
|
||||||
|
|
||||||
|
Changes:
|
||||||
|
|
||||||
|
- Make `fork_action.h` a public header (@patricoferris #769, reviewed by @talex5).
|
||||||
|
Allows other libraries to add new actions.
|
||||||
|
|
||||||
|
- Record trace event when spawning processes (@talex5 #749).
|
||||||
|
Spawning a subprocess can take a long time in some cases, so show it clearly in the traces.
|
||||||
|
|
||||||
|
- Eio_unix.Net: make some return types more polymorphic (@talex5 #744).
|
||||||
|
|
||||||
|
Bug fixes:
|
||||||
|
|
||||||
|
- Preserve backtraces in `fork_daemon` (@talex5 #779).
|
||||||
|
|
||||||
|
- Eio.Path: always use "/" as separator (@talex5 #743).
|
||||||
|
|
||||||
|
Linux backend:
|
||||||
|
|
||||||
|
- Allow `alloc_fixed_or_wait` to be cancelled (@talex5 #753).
|
||||||
|
|
||||||
|
- Avoid triggering a (harmless) TSan warning (@talex5 #754, reported by @avsm).
|
||||||
|
|
||||||
|
Windows backend:
|
||||||
|
|
||||||
|
- Unregister FDs on cancel (@talex5 #756).
|
||||||
|
Fixes `exception Unix.Unix_error(Unix.ENOTSOCK, "select", "")`.
|
||||||
|
|
||||||
|
- Work around problems in `Unix.getaddrinfo` (@talex5 #780).
|
||||||
|
Fixes e.g. `No addresses found for host name "127.0.0.1"`.
|
||||||
|
|
||||||
|
- Group `ECONNABORTED` with other connection reset errors (@talex5 #783).
|
||||||
|
|
||||||
|
- Check `has_symlink` for tests (@create2000 #771, reviewed by @patricoferris and @talex5).
|
||||||
|
|
||||||
|
- Improve `openat` error handling (@talex5 #742, reported by @kentookura).
|
||||||
|
Fixes `exception Unix.Unix_error(Unix.ENOENT, "openat", "")`.
|
||||||
|
|
||||||
|
Documentation:
|
||||||
|
|
||||||
|
- examples/fs: show how to read files while scanning (@talex5 #745).
|
||||||
|
|
||||||
|
- Add example to `Buf_read.seq` documentation (@talex5 #739, requested by @darrenldl and @rizo).
|
||||||
|
|
||||||
|
Build and test:
|
||||||
|
|
||||||
|
- Fix tests on OpenBSD (@talex5 #782).
|
||||||
|
|
||||||
|
- Add advice about using AI for code generation (@patricoferris #765, reviewed by @avsm and @talex5).
|
||||||
|
|
||||||
|
- Minor code cleanups (@talex5 #755).
|
||||||
|
|
||||||
|
- Define `struct clone_args` for linux-lts versions that don't have it (@copy #741, reviewed by @talex5).
|
||||||
|
|
||||||
|
- eio_linux: refactor fixed buffer code (@talex5 #752).
|
||||||
|
|
||||||
## v1.1
|
## v1.1
|
||||||
|
|
||||||
New features:
|
New features:
|
||||||
|
11
HACKING.md
11
HACKING.md
@ -135,4 +135,15 @@ Try to avoid making unnecessary changes; this makes review harder and clutters u
|
|||||||
`ocamlformat` may be useful to get badly messed up code to a baseline unformatted state,
|
`ocamlformat` may be useful to get badly messed up code to a baseline unformatted state,
|
||||||
from which human formatting can be added where needed.
|
from which human formatting can be added where needed.
|
||||||
|
|
||||||
|
## AI-generated Code
|
||||||
|
|
||||||
|
Contributing to Eio should not be done _solely_ using "AI tools" such as ChatGPT. This is for a few reasons:
|
||||||
|
|
||||||
|
1. **It obfuscates how you think**. Purely AI-generated code tells us little about how you think and the problems you might be having. This makes it harder to provide good feedback on PRs and issues.
|
||||||
|
2. **It is often more work to review**. Particularly for the OCaml ecosystem and libraries like Eio, it seems that these tools are not very good and generate a lot of believable code that is in actual fact completely wrong. PR comments and the code submitted with them can say completely different things.
|
||||||
|
3. **It is a grey area for licensing**. Models like ChatGPT have been trained on lots of code with different licenses and has been known to simply copy code as an answer to a prompt. We would like to avoid this headache as best we can.
|
||||||
|
|
||||||
|
Use AI tools, if you wish, to help you understand OCaml and Eio. Do not offload all of the work of a PR or a comment to these tools.
|
||||||
|
|
||||||
[dscheck]: https://github.com/ocaml-multicore/dscheck
|
[dscheck]: https://github.com/ocaml-multicore/dscheck
|
||||||
|
|
||||||
|
65
README.md
65
README.md
@ -79,9 +79,8 @@ Additionally, modern operating systems provide high-performance alternatives to
|
|||||||
For example, Linux's io_uring system has applications write the operations they want to perform to a ring buffer,
|
For example, Linux's io_uring system has applications write the operations they want to perform to a ring buffer,
|
||||||
which Linux handles asynchronously, and Eio can take advantage of this.
|
which Linux handles asynchronously, and Eio can take advantage of this.
|
||||||
|
|
||||||
Please try porting your programs to use Eio and submit PRs or open issues when you find problems.
|
You can always [fall back to using Lwt libraries](#lwt) to provide missing features if necessary.
|
||||||
Remember that you can always [fall back to using Lwt libraries](#lwt) to provide missing features if necessary.
|
See [Awesome Multicore OCaml][] for links to other projects using Eio.
|
||||||
See [Awesome Multicore OCaml][] for links to work migrating other projects to Eio.
|
|
||||||
|
|
||||||
## Eio packages
|
## Eio packages
|
||||||
|
|
||||||
@ -232,12 +231,7 @@ The green segments show when each fiber is running.
|
|||||||
Note that the output from `traceln` appears in the trace as well as on the console.
|
Note that the output from `traceln` appears in the trace as well as on the console.
|
||||||
In the eio-trace window, scrolling with the mouse or touchpad will zoom in or out of the diagram.
|
In the eio-trace window, scrolling with the mouse or touchpad will zoom in or out of the diagram.
|
||||||
|
|
||||||
There are various third-party tools that can also consume this data
|
Third-party tools, such as [Olly][], can also consume this data.
|
||||||
(but may currently require patches to support the new system):
|
|
||||||
|
|
||||||
- [Meio][] (Monitoring for Eio) provides an interactive console-based UI for exploring running fibers.
|
|
||||||
- [Olly][] can save Perfetto traces and report statistics.
|
|
||||||
|
|
||||||
[examples/trace](./examples/trace/) shows how to consume the events manually.
|
[examples/trace](./examples/trace/) shows how to consume the events manually.
|
||||||
|
|
||||||
## Cancellation
|
## Cancellation
|
||||||
@ -311,22 +305,23 @@ For example:
|
|||||||
```ocaml
|
```ocaml
|
||||||
# Eio_main.run @@ fun _env ->
|
# Eio_main.run @@ fun _env ->
|
||||||
Switch.run (fun sw ->
|
Switch.run (fun sw ->
|
||||||
Fiber.fork ~sw
|
for i = 1 to 3 do
|
||||||
(fun () -> for i = 1 to 3 do traceln "i = %d" i; Fiber.yield () done);
|
Fiber.fork ~sw (fun () ->
|
||||||
traceln "First thread forked";
|
traceln "Job %d starting" i;
|
||||||
Fiber.fork ~sw
|
Fiber.yield ();
|
||||||
(fun () -> for j = 1 to 3 do traceln "j = %d" j; Fiber.yield () done);
|
traceln "%d done" i;
|
||||||
traceln "Second thread forked; top-level code is finished"
|
);
|
||||||
);
|
done;
|
||||||
|
traceln "All child fibers forked";
|
||||||
|
);
|
||||||
traceln "Switch is finished";;
|
traceln "Switch is finished";;
|
||||||
+i = 1
|
+Job 1 starting
|
||||||
+First thread forked
|
+Job 2 starting
|
||||||
+j = 1
|
+Job 3 starting
|
||||||
+Second thread forked; top-level code is finished
|
+All child fibers forked
|
||||||
+i = 2
|
+1 done
|
||||||
+j = 2
|
+2 done
|
||||||
+i = 3
|
+3 done
|
||||||
+j = 3
|
|
||||||
+Switch is finished
|
+Switch is finished
|
||||||
- : unit = ()
|
- : unit = ()
|
||||||
```
|
```
|
||||||
@ -1015,12 +1010,8 @@ Usually you will only want one pool for an entire application, so the pool is ty
|
|||||||
let () =
|
let () =
|
||||||
Eio_main.run @@ fun env ->
|
Eio_main.run @@ fun env ->
|
||||||
Switch.run @@ fun sw ->
|
Switch.run @@ fun sw ->
|
||||||
let pool =
|
let dm = Eio.Stdenv.domain_mgr env in
|
||||||
Eio.Executor_pool.create
|
main ~pool:(Eio.Executor_pool.create ~sw ~domain_count:2 dm)
|
||||||
~sw (Eio.Stdenv.domain_mgr env)
|
|
||||||
~domain_count:4
|
|
||||||
in
|
|
||||||
main ~pool
|
|
||||||
```
|
```
|
||||||
|
|
||||||
The pool starts its domain workers immediately upon creation.
|
The pool starts its domain workers immediately upon creation.
|
||||||
@ -1034,11 +1025,7 @@ The total number of domains should not exceed `Domain.recommended_domain_count`
|
|||||||
We can run the previous example using an Executor Pool like this:
|
We can run the previous example using an Executor Pool like this:
|
||||||
|
|
||||||
```ocaml
|
```ocaml
|
||||||
let main ~domain_mgr =
|
let main ~pool =
|
||||||
Switch.run @@ fun sw ->
|
|
||||||
let pool =
|
|
||||||
Eio.Executor_pool.create ~sw domain_mgr ~domain_count:4
|
|
||||||
in
|
|
||||||
let test n =
|
let test n =
|
||||||
traceln "sum 1..%d = %d" n
|
traceln "sum 1..%d = %d" n
|
||||||
(Eio.Executor_pool.submit_exn pool ~weight:1.0
|
(Eio.Executor_pool.submit_exn pool ~weight:1.0
|
||||||
@ -1052,7 +1039,9 @@ let main ~domain_mgr =
|
|||||||
<!-- $MDX non-deterministic=output -->
|
<!-- $MDX non-deterministic=output -->
|
||||||
```ocaml
|
```ocaml
|
||||||
# Eio_main.run @@ fun env ->
|
# Eio_main.run @@ fun env ->
|
||||||
main ~domain_mgr:(Eio.Stdenv.domain_mgr env);;
|
Switch.run @@ fun sw ->
|
||||||
|
let dm = Eio.Stdenv.domain_mgr env in
|
||||||
|
main ~pool:(Eio.Executor_pool.create ~sw ~domain_count:2 dm)
|
||||||
+Starting CPU-intensive task...
|
+Starting CPU-intensive task...
|
||||||
+Starting CPU-intensive task...
|
+Starting CPU-intensive task...
|
||||||
+Finished
|
+Finished
|
||||||
@ -1632,7 +1621,8 @@ It can then be used like any other Eio flow:
|
|||||||
## Example Applications
|
## Example Applications
|
||||||
|
|
||||||
- [gemini-eio][] is a simple Gemini browser. It shows how to integrate Eio with `ocaml-tls` and `notty`.
|
- [gemini-eio][] is a simple Gemini browser. It shows how to integrate Eio with `ocaml-tls` and `notty`.
|
||||||
- [ocaml-multicore/retro-httpaf-bench](https://github.com/ocaml-multicore/retro-httpaf-bench) includes a simple HTTP server using Eio. It shows how to use Eio with `httpaf`, and how to use multiple domains for increased performance.
|
- [cohttp-eio/examples](https://github.com/mirage/ocaml-cohttp/tree/master/cohttp-eio/examples) shows how to use Eio with HTTP.
|
||||||
|
- [capnp-rpc](https://github.com/mirage/capnp-rpc) shows how to use Eio with Cap'n Proto.
|
||||||
- [Awesome Multicore OCaml][] lists many other projects.
|
- [Awesome Multicore OCaml][] lists many other projects.
|
||||||
|
|
||||||
## Integrations
|
## Integrations
|
||||||
@ -1906,7 +1896,6 @@ Some background about the effects system can be found in:
|
|||||||
[Eio.Condition]: https://ocaml-multicore.github.io/eio/eio/Eio/Condition/index.html
|
[Eio.Condition]: https://ocaml-multicore.github.io/eio/eio/Eio/Condition/index.html
|
||||||
[Domainslib]: https://github.com/ocaml-multicore/domainslib
|
[Domainslib]: https://github.com/ocaml-multicore/domainslib
|
||||||
[kcas]: https://github.com/ocaml-multicore/kcas
|
[kcas]: https://github.com/ocaml-multicore/kcas
|
||||||
[Meio]: https://github.com/tarides/meio
|
|
||||||
[Lambda Capabilities]: https://roscidus.com/blog/blog/2023/04/26/lambda-capabilities/
|
[Lambda Capabilities]: https://roscidus.com/blog/blog/2023/04/26/lambda-capabilities/
|
||||||
[Eio.Process]: https://ocaml-multicore.github.io/eio/eio/Eio/Process/index.html
|
[Eio.Process]: https://ocaml-multicore.github.io/eio/eio/Eio/Process/index.html
|
||||||
[Dev meetings]: https://docs.google.com/document/d/1ZBfbjAkvEkv9ldumpZV5VXrEc_HpPeYjHPW_TiwJe4Q
|
[Dev meetings]: https://docs.google.com/document/d/1ZBfbjAkvEkv9ldumpZV5VXrEc_HpPeYjHPW_TiwJe4Q
|
||||||
|
Binary file not shown.
@ -1,5 +1,5 @@
|
|||||||
<?xml version="1.0" encoding="UTF-8"?>
|
<?xml version="1.0" encoding="UTF-8"?>
|
||||||
<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" width="1280pt" height="152pt" viewBox="0 0 1280 152" version="1.1">
|
<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" width="1280pt" height="184pt" viewBox="0 0 1280 184" version="1.1">
|
||||||
<defs>
|
<defs>
|
||||||
<g>
|
<g>
|
||||||
<symbol overflow="visible" id="glyph0-0">
|
<symbol overflow="visible" id="glyph0-0">
|
||||||
@ -81,489 +81,450 @@
|
|||||||
<path style="stroke:none;" d="M 0.40625 1.421875 L 0.40625 -5.640625 L 4.40625 -5.640625 L 4.40625 1.421875 Z M 0.84375 0.96875 L 3.953125 0.96875 L 3.953125 -5.1875 L 0.84375 -5.1875 Z M 0.84375 0.96875 "/>
|
<path style="stroke:none;" d="M 0.40625 1.421875 L 0.40625 -5.640625 L 4.40625 -5.640625 L 4.40625 1.421875 Z M 0.84375 0.96875 L 3.953125 0.96875 L 3.953125 -5.1875 L 0.84375 -5.1875 Z M 0.84375 0.96875 "/>
|
||||||
</symbol>
|
</symbol>
|
||||||
<symbol overflow="visible" id="glyph1-1">
|
<symbol overflow="visible" id="glyph1-1">
|
||||||
<path style="stroke:none;" d="M 0.75 -4.375 L 1.46875 -4.375 L 1.46875 0 L 0.75 0 Z M 0.75 -6.078125 L 1.46875 -6.078125 L 1.46875 -5.171875 L 0.75 -5.171875 Z M 0.75 -6.078125 "/>
|
<path style="stroke:none;" d="M 0.78125 -5.828125 L 1.578125 -5.828125 L 1.578125 -0.40625 C 1.578125 0.300781 1.441406 0.8125 1.171875 1.125 C 0.910156 1.445312 0.484375 1.609375 -0.109375 1.609375 L -0.421875 1.609375 L -0.421875 0.9375 L -0.171875 0.9375 C 0.179688 0.9375 0.425781 0.835938 0.5625 0.640625 C 0.707031 0.453125 0.78125 0.101562 0.78125 -0.40625 Z M 0.78125 -5.828125 "/>
|
||||||
</symbol>
|
</symbol>
|
||||||
<symbol overflow="visible" id="glyph1-2">
|
<symbol overflow="visible" id="glyph1-2">
|
||||||
<path style="stroke:none;" d=""/>
|
|
||||||
</symbol>
|
|
||||||
<symbol overflow="visible" id="glyph1-3">
|
|
||||||
<path style="stroke:none;" d="M 0.84375 -3.640625 L 5.859375 -3.640625 L 5.859375 -2.984375 L 0.84375 -2.984375 Z M 0.84375 -2.046875 L 5.859375 -2.046875 L 5.859375 -1.375 L 0.84375 -1.375 Z M 0.84375 -2.046875 "/>
|
|
||||||
</symbol>
|
|
||||||
<symbol overflow="visible" id="glyph1-4">
|
|
||||||
<path style="stroke:none;" d="M 1 -0.671875 L 2.28125 -0.671875 L 2.28125 -5.109375 L 0.875 -4.828125 L 0.875 -5.546875 L 2.28125 -5.828125 L 3.0625 -5.828125 L 3.0625 -0.671875 L 4.359375 -0.671875 L 4.359375 0 L 1 0 Z M 1 -0.671875 "/>
|
|
||||||
</symbol>
|
|
||||||
<symbol overflow="visible" id="glyph1-5">
|
|
||||||
<path style="stroke:none;" d="M 1.53125 -0.671875 L 4.296875 -0.671875 L 4.296875 0 L 0.59375 0 L 0.59375 -0.671875 C 0.882812 -0.972656 1.289062 -1.382812 1.8125 -1.90625 C 2.332031 -2.4375 2.65625 -2.773438 2.78125 -2.921875 C 3.039062 -3.203125 3.21875 -3.441406 3.3125 -3.640625 C 3.414062 -3.835938 3.46875 -4.03125 3.46875 -4.21875 C 3.46875 -4.53125 3.359375 -4.785156 3.140625 -4.984375 C 2.921875 -5.179688 2.640625 -5.28125 2.296875 -5.28125 C 2.046875 -5.28125 1.78125 -5.234375 1.5 -5.140625 C 1.226562 -5.054688 0.9375 -4.925781 0.625 -4.75 L 0.625 -5.546875 C 0.945312 -5.679688 1.242188 -5.78125 1.515625 -5.84375 C 1.796875 -5.90625 2.050781 -5.9375 2.28125 -5.9375 C 2.882812 -5.9375 3.363281 -5.785156 3.71875 -5.484375 C 4.082031 -5.179688 4.265625 -4.78125 4.265625 -4.28125 C 4.265625 -4.039062 4.21875 -3.8125 4.125 -3.59375 C 4.03125 -3.375 3.867188 -3.117188 3.640625 -2.828125 C 3.566406 -2.753906 3.351562 -2.535156 3 -2.171875 C 2.65625 -1.816406 2.164062 -1.316406 1.53125 -0.671875 Z M 1.53125 -0.671875 "/>
|
|
||||||
</symbol>
|
|
||||||
<symbol overflow="visible" id="glyph1-6">
|
|
||||||
<path style="stroke:none;" d="M 3.25 -3.140625 C 3.625 -3.066406 3.914062 -2.898438 4.125 -2.640625 C 4.34375 -2.390625 4.453125 -2.078125 4.453125 -1.703125 C 4.453125 -1.117188 4.253906 -0.671875 3.859375 -0.359375 C 3.460938 -0.046875 2.898438 0.109375 2.171875 0.109375 C 1.921875 0.109375 1.664062 0.0820312 1.40625 0.03125 C 1.15625 -0.0078125 0.890625 -0.078125 0.609375 -0.171875 L 0.609375 -0.9375 C 0.828125 -0.8125 1.066406 -0.710938 1.328125 -0.640625 C 1.585938 -0.578125 1.859375 -0.546875 2.140625 -0.546875 C 2.640625 -0.546875 3.019531 -0.644531 3.28125 -0.84375 C 3.539062 -1.039062 3.671875 -1.328125 3.671875 -1.703125 C 3.671875 -2.046875 3.546875 -2.3125 3.296875 -2.5 C 3.054688 -2.695312 2.722656 -2.796875 2.296875 -2.796875 L 1.625 -2.796875 L 1.625 -3.4375 L 2.328125 -3.4375 C 2.710938 -3.4375 3.007812 -3.515625 3.21875 -3.671875 C 3.425781 -3.828125 3.53125 -4.050781 3.53125 -4.34375 C 3.53125 -4.644531 3.421875 -4.875 3.203125 -5.03125 C 2.992188 -5.195312 2.691406 -5.28125 2.296875 -5.28125 C 2.078125 -5.28125 1.84375 -5.253906 1.59375 -5.203125 C 1.351562 -5.160156 1.082031 -5.085938 0.78125 -4.984375 L 0.78125 -5.6875 C 1.082031 -5.769531 1.363281 -5.832031 1.625 -5.875 C 1.882812 -5.914062 2.132812 -5.9375 2.375 -5.9375 C 2.96875 -5.9375 3.4375 -5.800781 3.78125 -5.53125 C 4.132812 -5.257812 4.3125 -4.890625 4.3125 -4.421875 C 4.3125 -4.097656 4.21875 -3.828125 4.03125 -3.609375 C 3.851562 -3.390625 3.59375 -3.234375 3.25 -3.140625 Z M 3.25 -3.140625 "/>
|
|
||||||
</symbol>
|
|
||||||
<symbol overflow="visible" id="glyph1-7">
|
|
||||||
<path style="stroke:none;" d="M 0.78125 -5.828125 L 4.140625 -5.828125 L 4.140625 -5.171875 L 1.578125 -5.171875 L 1.578125 -3.453125 L 3.890625 -3.453125 L 3.890625 -2.78125 L 1.578125 -2.78125 L 1.578125 0 L 0.78125 0 Z M 0.78125 -5.828125 "/>
|
|
||||||
</symbol>
|
|
||||||
<symbol overflow="visible" id="glyph1-8">
|
|
||||||
<path style="stroke:none;" d="M 3.296875 -3.703125 C 3.210938 -3.753906 3.125 -3.789062 3.03125 -3.8125 C 2.9375 -3.832031 2.832031 -3.84375 2.71875 -3.84375 C 2.3125 -3.84375 2 -3.707031 1.78125 -3.4375 C 1.5625 -3.175781 1.453125 -2.800781 1.453125 -2.3125 L 1.453125 0 L 0.734375 0 L 0.734375 -4.375 L 1.453125 -4.375 L 1.453125 -3.703125 C 1.597656 -3.960938 1.789062 -4.15625 2.03125 -4.28125 C 2.28125 -4.414062 2.578125 -4.484375 2.921875 -4.484375 C 2.972656 -4.484375 3.023438 -4.476562 3.078125 -4.46875 C 3.140625 -4.46875 3.207031 -4.457031 3.28125 -4.4375 Z M 3.296875 -3.703125 "/>
|
|
||||||
</symbol>
|
|
||||||
<symbol overflow="visible" id="glyph1-9">
|
|
||||||
<path style="stroke:none;" d="M 3.546875 -4.25 L 3.546875 -3.5625 C 3.335938 -3.664062 3.125 -3.742188 2.90625 -3.796875 C 2.6875 -3.847656 2.460938 -3.875 2.234375 -3.875 C 1.878906 -3.875 1.609375 -3.816406 1.421875 -3.703125 C 1.242188 -3.597656 1.15625 -3.4375 1.15625 -3.21875 C 1.15625 -3.050781 1.21875 -2.921875 1.34375 -2.828125 C 1.476562 -2.734375 1.738281 -2.644531 2.125 -2.5625 L 2.375 -2.5 C 2.882812 -2.394531 3.242188 -2.242188 3.453125 -2.046875 C 3.671875 -1.847656 3.78125 -1.566406 3.78125 -1.203125 C 3.78125 -0.796875 3.617188 -0.472656 3.296875 -0.234375 C 2.972656 -0.00390625 2.53125 0.109375 1.96875 0.109375 C 1.738281 0.109375 1.492188 0.0820312 1.234375 0.03125 C 0.984375 -0.0078125 0.71875 -0.0703125 0.4375 -0.15625 L 0.4375 -0.90625 C 0.695312 -0.769531 0.957031 -0.664062 1.21875 -0.59375 C 1.476562 -0.519531 1.734375 -0.484375 1.984375 -0.484375 C 2.328125 -0.484375 2.585938 -0.539062 2.765625 -0.65625 C 2.953125 -0.78125 3.046875 -0.945312 3.046875 -1.15625 C 3.046875 -1.351562 2.976562 -1.503906 2.84375 -1.609375 C 2.707031 -1.710938 2.421875 -1.8125 1.984375 -1.90625 L 1.734375 -1.96875 C 1.285156 -2.0625 0.960938 -2.203125 0.765625 -2.390625 C 0.566406 -2.585938 0.46875 -2.851562 0.46875 -3.1875 C 0.46875 -3.601562 0.613281 -3.921875 0.90625 -4.140625 C 1.195312 -4.367188 1.609375 -4.484375 2.140625 -4.484375 C 2.410156 -4.484375 2.660156 -4.460938 2.890625 -4.421875 C 3.128906 -4.378906 3.347656 -4.320312 3.546875 -4.25 Z M 3.546875 -4.25 "/>
|
|
||||||
</symbol>
|
|
||||||
<symbol overflow="visible" id="glyph1-10">
|
|
||||||
<path style="stroke:none;" d="M 1.46875 -5.625 L 1.46875 -4.375 L 2.953125 -4.375 L 2.953125 -3.8125 L 1.46875 -3.8125 L 1.46875 -1.4375 C 1.46875 -1.082031 1.515625 -0.851562 1.609375 -0.75 C 1.710938 -0.65625 1.910156 -0.609375 2.203125 -0.609375 L 2.953125 -0.609375 L 2.953125 0 L 2.203125 0 C 1.648438 0 1.269531 -0.101562 1.0625 -0.3125 C 0.851562 -0.519531 0.75 -0.894531 0.75 -1.4375 L 0.75 -3.8125 L 0.21875 -3.8125 L 0.21875 -4.375 L 0.75 -4.375 L 0.75 -5.625 Z M 1.46875 -5.625 "/>
|
|
||||||
</symbol>
|
|
||||||
<symbol overflow="visible" id="glyph1-11">
|
|
||||||
<path style="stroke:none;" d="M 4.390625 -2.640625 L 4.390625 0 L 3.671875 0 L 3.671875 -2.625 C 3.671875 -3.03125 3.585938 -3.335938 3.421875 -3.546875 C 3.265625 -3.753906 3.023438 -3.859375 2.703125 -3.859375 C 2.316406 -3.859375 2.007812 -3.734375 1.78125 -3.484375 C 1.5625 -3.234375 1.453125 -2.894531 1.453125 -2.46875 L 1.453125 0 L 0.734375 0 L 0.734375 -6.078125 L 1.453125 -6.078125 L 1.453125 -3.703125 C 1.617188 -3.960938 1.816406 -4.15625 2.046875 -4.28125 C 2.285156 -4.414062 2.554688 -4.484375 2.859375 -4.484375 C 3.367188 -4.484375 3.75 -4.328125 4 -4.015625 C 4.257812 -3.703125 4.390625 -3.242188 4.390625 -2.640625 Z M 4.390625 -2.640625 "/>
|
|
||||||
</symbol>
|
|
||||||
<symbol overflow="visible" id="glyph1-12">
|
|
||||||
<path style="stroke:none;" d="M 4.5 -2.375 L 4.5 -2.015625 L 1.1875 -2.015625 C 1.21875 -1.523438 1.367188 -1.148438 1.640625 -0.890625 C 1.910156 -0.628906 2.28125 -0.5 2.75 -0.5 C 3.03125 -0.5 3.300781 -0.53125 3.5625 -0.59375 C 3.820312 -0.664062 4.078125 -0.769531 4.328125 -0.90625 L 4.328125 -0.21875 C 4.066406 -0.113281 3.800781 -0.0351562 3.53125 0.015625 C 3.257812 0.078125 2.988281 0.109375 2.71875 0.109375 C 2.019531 0.109375 1.460938 -0.09375 1.046875 -0.5 C 0.640625 -0.90625 0.4375 -1.453125 0.4375 -2.140625 C 0.4375 -2.859375 0.628906 -3.425781 1.015625 -3.84375 C 1.410156 -4.269531 1.9375 -4.484375 2.59375 -4.484375 C 3.175781 -4.484375 3.640625 -4.289062 3.984375 -3.90625 C 4.328125 -3.53125 4.5 -3.019531 4.5 -2.375 Z M 3.78125 -2.578125 C 3.769531 -2.972656 3.65625 -3.285156 3.4375 -3.515625 C 3.226562 -3.753906 2.945312 -3.875 2.59375 -3.875 C 2.195312 -3.875 1.875 -3.757812 1.625 -3.53125 C 1.382812 -3.300781 1.25 -2.984375 1.21875 -2.578125 Z M 3.78125 -2.578125 "/>
|
|
||||||
</symbol>
|
|
||||||
<symbol overflow="visible" id="glyph1-13">
|
|
||||||
<path style="stroke:none;" d="M 2.75 -2.203125 C 2.164062 -2.203125 1.757812 -2.132812 1.53125 -2 C 1.3125 -1.863281 1.203125 -1.640625 1.203125 -1.328125 C 1.203125 -1.066406 1.285156 -0.859375 1.453125 -0.703125 C 1.617188 -0.554688 1.847656 -0.484375 2.140625 -0.484375 C 2.535156 -0.484375 2.851562 -0.625 3.09375 -0.90625 C 3.332031 -1.195312 3.453125 -1.578125 3.453125 -2.046875 L 3.453125 -2.203125 Z M 4.171875 -2.5 L 4.171875 0 L 3.453125 0 L 3.453125 -0.671875 C 3.296875 -0.398438 3.09375 -0.203125 2.84375 -0.078125 C 2.601562 0.046875 2.304688 0.109375 1.953125 0.109375 C 1.503906 0.109375 1.144531 -0.015625 0.875 -0.265625 C 0.613281 -0.515625 0.484375 -0.851562 0.484375 -1.28125 C 0.484375 -1.769531 0.644531 -2.140625 0.96875 -2.390625 C 1.300781 -2.640625 1.796875 -2.765625 2.453125 -2.765625 L 3.453125 -2.765625 L 3.453125 -2.828125 C 3.453125 -3.160156 3.34375 -3.414062 3.125 -3.59375 C 2.914062 -3.78125 2.613281 -3.875 2.21875 -3.875 C 1.96875 -3.875 1.722656 -3.84375 1.484375 -3.78125 C 1.242188 -3.71875 1.015625 -3.628906 0.796875 -3.515625 L 0.796875 -4.171875 C 1.066406 -4.273438 1.320312 -4.351562 1.5625 -4.40625 C 1.8125 -4.457031 2.054688 -4.484375 2.296875 -4.484375 C 2.921875 -4.484375 3.390625 -4.316406 3.703125 -3.984375 C 4.015625 -3.660156 4.171875 -3.164062 4.171875 -2.5 Z M 4.171875 -2.5 "/>
|
|
||||||
</symbol>
|
|
||||||
<symbol overflow="visible" id="glyph1-14">
|
|
||||||
<path style="stroke:none;" d="M 3.640625 -3.71875 L 3.640625 -6.078125 L 4.359375 -6.078125 L 4.359375 0 L 3.640625 0 L 3.640625 -0.65625 C 3.484375 -0.394531 3.289062 -0.203125 3.0625 -0.078125 C 2.832031 0.046875 2.554688 0.109375 2.234375 0.109375 C 1.703125 0.109375 1.269531 -0.0976562 0.9375 -0.515625 C 0.601562 -0.941406 0.4375 -1.5 0.4375 -2.1875 C 0.4375 -2.875 0.601562 -3.425781 0.9375 -3.84375 C 1.269531 -4.269531 1.703125 -4.484375 2.234375 -4.484375 C 2.554688 -4.484375 2.832031 -4.421875 3.0625 -4.296875 C 3.289062 -4.171875 3.484375 -3.976562 3.640625 -3.71875 Z M 1.1875 -2.1875 C 1.1875 -1.65625 1.296875 -1.238281 1.515625 -0.9375 C 1.734375 -0.632812 2.03125 -0.484375 2.40625 -0.484375 C 2.789062 -0.484375 3.09375 -0.632812 3.3125 -0.9375 C 3.53125 -1.238281 3.640625 -1.65625 3.640625 -2.1875 C 3.640625 -2.71875 3.53125 -3.128906 3.3125 -3.421875 C 3.09375 -3.722656 2.789062 -3.875 2.40625 -3.875 C 2.03125 -3.875 1.734375 -3.722656 1.515625 -3.421875 C 1.296875 -3.128906 1.1875 -2.71875 1.1875 -2.1875 Z M 1.1875 -2.1875 "/>
|
|
||||||
</symbol>
|
|
||||||
<symbol overflow="visible" id="glyph1-15">
|
|
||||||
<path style="stroke:none;" d="M 2.96875 -6.078125 L 2.96875 -5.484375 L 2.28125 -5.484375 C 2.019531 -5.484375 1.835938 -5.429688 1.734375 -5.328125 C 1.640625 -5.222656 1.59375 -5.035156 1.59375 -4.765625 L 1.59375 -4.375 L 2.78125 -4.375 L 2.78125 -3.8125 L 1.59375 -3.8125 L 1.59375 0 L 0.875 0 L 0.875 -3.8125 L 0.1875 -3.8125 L 0.1875 -4.375 L 0.875 -4.375 L 0.875 -4.6875 C 0.875 -5.164062 0.984375 -5.515625 1.203125 -5.734375 C 1.429688 -5.960938 1.796875 -6.078125 2.296875 -6.078125 Z M 2.96875 -6.078125 "/>
|
|
||||||
</symbol>
|
|
||||||
<symbol overflow="visible" id="glyph1-16">
|
|
||||||
<path style="stroke:none;" d="M 2.453125 -3.875 C 2.066406 -3.875 1.757812 -3.722656 1.53125 -3.421875 C 1.3125 -3.117188 1.203125 -2.707031 1.203125 -2.1875 C 1.203125 -1.664062 1.3125 -1.253906 1.53125 -0.953125 C 1.757812 -0.648438 2.066406 -0.5 2.453125 -0.5 C 2.835938 -0.5 3.140625 -0.648438 3.359375 -0.953125 C 3.585938 -1.253906 3.703125 -1.664062 3.703125 -2.1875 C 3.703125 -2.707031 3.585938 -3.117188 3.359375 -3.421875 C 3.140625 -3.722656 2.835938 -3.875 2.453125 -3.875 Z M 2.453125 -4.484375 C 3.078125 -4.484375 3.566406 -4.28125 3.921875 -3.875 C 4.273438 -3.46875 4.453125 -2.90625 4.453125 -2.1875 C 4.453125 -1.46875 4.273438 -0.90625 3.921875 -0.5 C 3.566406 -0.09375 3.078125 0.109375 2.453125 0.109375 C 1.828125 0.109375 1.332031 -0.09375 0.96875 -0.5 C 0.613281 -0.90625 0.4375 -1.46875 0.4375 -2.1875 C 0.4375 -2.90625 0.613281 -3.46875 0.96875 -3.875 C 1.332031 -4.28125 1.828125 -4.484375 2.453125 -4.484375 Z M 2.453125 -4.484375 "/>
|
<path style="stroke:none;" d="M 2.453125 -3.875 C 2.066406 -3.875 1.757812 -3.722656 1.53125 -3.421875 C 1.3125 -3.117188 1.203125 -2.707031 1.203125 -2.1875 C 1.203125 -1.664062 1.3125 -1.253906 1.53125 -0.953125 C 1.757812 -0.648438 2.066406 -0.5 2.453125 -0.5 C 2.835938 -0.5 3.140625 -0.648438 3.359375 -0.953125 C 3.585938 -1.253906 3.703125 -1.664062 3.703125 -2.1875 C 3.703125 -2.707031 3.585938 -3.117188 3.359375 -3.421875 C 3.140625 -3.722656 2.835938 -3.875 2.453125 -3.875 Z M 2.453125 -4.484375 C 3.078125 -4.484375 3.566406 -4.28125 3.921875 -3.875 C 4.273438 -3.46875 4.453125 -2.90625 4.453125 -2.1875 C 4.453125 -1.46875 4.273438 -0.90625 3.921875 -0.5 C 3.566406 -0.09375 3.078125 0.109375 2.453125 0.109375 C 1.828125 0.109375 1.332031 -0.09375 0.96875 -0.5 C 0.613281 -0.90625 0.4375 -1.46875 0.4375 -2.1875 C 0.4375 -2.90625 0.613281 -3.46875 0.96875 -3.875 C 1.332031 -4.28125 1.828125 -4.484375 2.453125 -4.484375 Z M 2.453125 -4.484375 "/>
|
||||||
</symbol>
|
</symbol>
|
||||||
<symbol overflow="visible" id="glyph1-17">
|
<symbol overflow="visible" id="glyph1-3">
|
||||||
<path style="stroke:none;" d="M 0.734375 -6.078125 L 1.453125 -6.078125 L 1.453125 -2.484375 L 3.59375 -4.375 L 4.515625 -4.375 L 2.1875 -2.328125 L 4.609375 0 L 3.671875 0 L 1.453125 -2.140625 L 1.453125 0 L 0.734375 0 Z M 0.734375 -6.078125 "/>
|
<path style="stroke:none;" d="M 3.890625 -2.1875 C 3.890625 -2.71875 3.78125 -3.128906 3.5625 -3.421875 C 3.351562 -3.722656 3.054688 -3.875 2.671875 -3.875 C 2.296875 -3.875 2 -3.722656 1.78125 -3.421875 C 1.5625 -3.128906 1.453125 -2.71875 1.453125 -2.1875 C 1.453125 -1.65625 1.5625 -1.238281 1.78125 -0.9375 C 2 -0.632812 2.296875 -0.484375 2.671875 -0.484375 C 3.054688 -0.484375 3.351562 -0.632812 3.5625 -0.9375 C 3.78125 -1.238281 3.890625 -1.65625 3.890625 -2.1875 Z M 1.453125 -3.71875 C 1.597656 -3.976562 1.785156 -4.171875 2.015625 -4.296875 C 2.253906 -4.421875 2.53125 -4.484375 2.84375 -4.484375 C 3.375 -4.484375 3.804688 -4.269531 4.140625 -3.84375 C 4.472656 -3.425781 4.640625 -2.875 4.640625 -2.1875 C 4.640625 -1.5 4.472656 -0.941406 4.140625 -0.515625 C 3.804688 -0.0976562 3.375 0.109375 2.84375 0.109375 C 2.53125 0.109375 2.253906 0.046875 2.015625 -0.078125 C 1.785156 -0.203125 1.597656 -0.394531 1.453125 -0.65625 L 1.453125 0 L 0.734375 0 L 0.734375 -6.078125 L 1.453125 -6.078125 Z M 1.453125 -3.71875 "/>
|
||||||
</symbol>
|
</symbol>
|
||||||
<symbol overflow="visible" id="glyph1-18">
|
<symbol overflow="visible" id="glyph1-4">
|
||||||
<path style="stroke:none;" d="M 0.75 -4.375 L 1.46875 -4.375 L 1.46875 0.078125 C 1.46875 0.640625 1.363281 1.046875 1.15625 1.296875 C 0.945312 1.546875 0.601562 1.671875 0.125 1.671875 L -0.140625 1.671875 L -0.140625 1.0625 L 0.046875 1.0625 C 0.316406 1.0625 0.5 0.992188 0.59375 0.859375 C 0.695312 0.734375 0.75 0.472656 0.75 0.078125 Z M 0.75 -6.078125 L 1.46875 -6.078125 L 1.46875 -5.171875 L 0.75 -5.171875 Z M 0.75 -6.078125 "/>
|
<path style="stroke:none;" d=""/>
|
||||||
</symbol>
|
</symbol>
|
||||||
<symbol overflow="visible" id="glyph1-19">
|
<symbol overflow="visible" id="glyph1-5">
|
||||||
<path style="stroke:none;" d="M 4.28125 -5.640625 L 4.28125 -4.875 C 3.976562 -5.019531 3.691406 -5.125 3.421875 -5.1875 C 3.160156 -5.257812 2.910156 -5.296875 2.671875 -5.296875 C 2.234375 -5.296875 1.898438 -5.210938 1.671875 -5.046875 C 1.441406 -4.878906 1.328125 -4.644531 1.328125 -4.34375 C 1.328125 -4.082031 1.398438 -3.882812 1.546875 -3.75 C 1.703125 -3.625 2 -3.519531 2.4375 -3.4375 L 2.90625 -3.34375 C 3.5 -3.226562 3.9375 -3.03125 4.21875 -2.75 C 4.5 -2.46875 4.640625 -2.085938 4.640625 -1.609375 C 4.640625 -1.046875 4.445312 -0.617188 4.0625 -0.328125 C 3.6875 -0.0351562 3.132812 0.109375 2.40625 0.109375 C 2.125 0.109375 1.828125 0.078125 1.515625 0.015625 C 1.203125 -0.046875 0.878906 -0.140625 0.546875 -0.265625 L 0.546875 -1.078125 C 0.867188 -0.890625 1.179688 -0.75 1.484375 -0.65625 C 1.796875 -0.570312 2.101562 -0.53125 2.40625 -0.53125 C 2.851562 -0.53125 3.195312 -0.617188 3.4375 -0.796875 C 3.6875 -0.972656 3.8125 -1.222656 3.8125 -1.546875 C 3.8125 -1.835938 3.722656 -2.0625 3.546875 -2.21875 C 3.367188 -2.382812 3.082031 -2.507812 2.6875 -2.59375 L 2.203125 -2.6875 C 1.609375 -2.800781 1.179688 -2.984375 0.921875 -3.234375 C 0.660156 -3.484375 0.53125 -3.832031 0.53125 -4.28125 C 0.53125 -4.789062 0.710938 -5.191406 1.078125 -5.484375 C 1.441406 -5.785156 1.941406 -5.9375 2.578125 -5.9375 C 2.847656 -5.9375 3.125 -5.910156 3.40625 -5.859375 C 3.695312 -5.816406 3.988281 -5.742188 4.28125 -5.640625 Z M 4.28125 -5.640625 "/>
|
<path style="stroke:none;" d="M 1 -0.671875 L 2.28125 -0.671875 L 2.28125 -5.109375 L 0.875 -4.828125 L 0.875 -5.546875 L 2.28125 -5.828125 L 3.0625 -5.828125 L 3.0625 -0.671875 L 4.359375 -0.671875 L 4.359375 0 L 1 0 Z M 1 -0.671875 "/>
|
||||||
</symbol>
|
</symbol>
|
||||||
<symbol overflow="visible" id="glyph1-20">
|
<symbol overflow="visible" id="glyph1-6">
|
||||||
<path style="stroke:none;" d="M 3.90625 -4.203125 L 3.90625 -3.53125 C 3.695312 -3.644531 3.488281 -3.726562 3.28125 -3.78125 C 3.082031 -3.84375 2.878906 -3.875 2.671875 -3.875 C 2.203125 -3.875 1.835938 -3.722656 1.578125 -3.421875 C 1.328125 -3.128906 1.203125 -2.71875 1.203125 -2.1875 C 1.203125 -1.65625 1.328125 -1.238281 1.578125 -0.9375 C 1.835938 -0.644531 2.203125 -0.5 2.671875 -0.5 C 2.878906 -0.5 3.082031 -0.523438 3.28125 -0.578125 C 3.488281 -0.640625 3.695312 -0.722656 3.90625 -0.828125 L 3.90625 -0.171875 C 3.707031 -0.078125 3.5 -0.0078125 3.28125 0.03125 C 3.0625 0.0820312 2.832031 0.109375 2.59375 0.109375 C 1.9375 0.109375 1.410156 -0.09375 1.015625 -0.5 C 0.628906 -0.914062 0.4375 -1.476562 0.4375 -2.1875 C 0.4375 -2.894531 0.632812 -3.453125 1.03125 -3.859375 C 1.425781 -4.273438 1.960938 -4.484375 2.640625 -4.484375 C 2.859375 -4.484375 3.070312 -4.457031 3.28125 -4.40625 C 3.5 -4.363281 3.707031 -4.296875 3.90625 -4.203125 Z M 3.90625 -4.203125 "/>
|
<path style="stroke:none;" d="M 3.546875 -4.25 L 3.546875 -3.5625 C 3.335938 -3.664062 3.125 -3.742188 2.90625 -3.796875 C 2.6875 -3.847656 2.460938 -3.875 2.234375 -3.875 C 1.878906 -3.875 1.609375 -3.816406 1.421875 -3.703125 C 1.242188 -3.597656 1.15625 -3.4375 1.15625 -3.21875 C 1.15625 -3.050781 1.21875 -2.921875 1.34375 -2.828125 C 1.476562 -2.734375 1.738281 -2.644531 2.125 -2.5625 L 2.375 -2.5 C 2.882812 -2.394531 3.242188 -2.242188 3.453125 -2.046875 C 3.671875 -1.847656 3.78125 -1.566406 3.78125 -1.203125 C 3.78125 -0.796875 3.617188 -0.472656 3.296875 -0.234375 C 2.972656 -0.00390625 2.53125 0.109375 1.96875 0.109375 C 1.738281 0.109375 1.492188 0.0820312 1.234375 0.03125 C 0.984375 -0.0078125 0.71875 -0.0703125 0.4375 -0.15625 L 0.4375 -0.90625 C 0.695312 -0.769531 0.957031 -0.664062 1.21875 -0.59375 C 1.476562 -0.519531 1.734375 -0.484375 1.984375 -0.484375 C 2.328125 -0.484375 2.585938 -0.539062 2.765625 -0.65625 C 2.953125 -0.78125 3.046875 -0.945312 3.046875 -1.15625 C 3.046875 -1.351562 2.976562 -1.503906 2.84375 -1.609375 C 2.707031 -1.710938 2.421875 -1.8125 1.984375 -1.90625 L 1.734375 -1.96875 C 1.285156 -2.0625 0.960938 -2.203125 0.765625 -2.390625 C 0.566406 -2.585938 0.46875 -2.851562 0.46875 -3.1875 C 0.46875 -3.601562 0.613281 -3.921875 0.90625 -4.140625 C 1.195312 -4.367188 1.609375 -4.484375 2.140625 -4.484375 C 2.410156 -4.484375 2.660156 -4.460938 2.890625 -4.421875 C 3.128906 -4.378906 3.347656 -4.320312 3.546875 -4.25 Z M 3.546875 -4.25 "/>
|
||||||
</symbol>
|
</symbol>
|
||||||
<symbol overflow="visible" id="glyph1-21">
|
<symbol overflow="visible" id="glyph1-7">
|
||||||
|
<path style="stroke:none;" d="M 1.46875 -5.625 L 1.46875 -4.375 L 2.953125 -4.375 L 2.953125 -3.8125 L 1.46875 -3.8125 L 1.46875 -1.4375 C 1.46875 -1.082031 1.515625 -0.851562 1.609375 -0.75 C 1.710938 -0.65625 1.910156 -0.609375 2.203125 -0.609375 L 2.953125 -0.609375 L 2.953125 0 L 2.203125 0 C 1.648438 0 1.269531 -0.101562 1.0625 -0.3125 C 0.851562 -0.519531 0.75 -0.894531 0.75 -1.4375 L 0.75 -3.8125 L 0.21875 -3.8125 L 0.21875 -4.375 L 0.75 -4.375 L 0.75 -5.625 Z M 1.46875 -5.625 "/>
|
||||||
|
</symbol>
|
||||||
|
<symbol overflow="visible" id="glyph1-8">
|
||||||
|
<path style="stroke:none;" d="M 2.75 -2.203125 C 2.164062 -2.203125 1.757812 -2.132812 1.53125 -2 C 1.3125 -1.863281 1.203125 -1.640625 1.203125 -1.328125 C 1.203125 -1.066406 1.285156 -0.859375 1.453125 -0.703125 C 1.617188 -0.554688 1.847656 -0.484375 2.140625 -0.484375 C 2.535156 -0.484375 2.851562 -0.625 3.09375 -0.90625 C 3.332031 -1.195312 3.453125 -1.578125 3.453125 -2.046875 L 3.453125 -2.203125 Z M 4.171875 -2.5 L 4.171875 0 L 3.453125 0 L 3.453125 -0.671875 C 3.296875 -0.398438 3.09375 -0.203125 2.84375 -0.078125 C 2.601562 0.046875 2.304688 0.109375 1.953125 0.109375 C 1.503906 0.109375 1.144531 -0.015625 0.875 -0.265625 C 0.613281 -0.515625 0.484375 -0.851562 0.484375 -1.28125 C 0.484375 -1.769531 0.644531 -2.140625 0.96875 -2.390625 C 1.300781 -2.640625 1.796875 -2.765625 2.453125 -2.765625 L 3.453125 -2.765625 L 3.453125 -2.828125 C 3.453125 -3.160156 3.34375 -3.414062 3.125 -3.59375 C 2.914062 -3.78125 2.613281 -3.875 2.21875 -3.875 C 1.96875 -3.875 1.722656 -3.84375 1.484375 -3.78125 C 1.242188 -3.71875 1.015625 -3.628906 0.796875 -3.515625 L 0.796875 -4.171875 C 1.066406 -4.273438 1.320312 -4.351562 1.5625 -4.40625 C 1.8125 -4.457031 2.054688 -4.484375 2.296875 -4.484375 C 2.921875 -4.484375 3.390625 -4.316406 3.703125 -3.984375 C 4.015625 -3.660156 4.171875 -3.164062 4.171875 -2.5 Z M 4.171875 -2.5 "/>
|
||||||
|
</symbol>
|
||||||
|
<symbol overflow="visible" id="glyph1-9">
|
||||||
|
<path style="stroke:none;" d="M 3.296875 -3.703125 C 3.210938 -3.753906 3.125 -3.789062 3.03125 -3.8125 C 2.9375 -3.832031 2.832031 -3.84375 2.71875 -3.84375 C 2.3125 -3.84375 2 -3.707031 1.78125 -3.4375 C 1.5625 -3.175781 1.453125 -2.800781 1.453125 -2.3125 L 1.453125 0 L 0.734375 0 L 0.734375 -4.375 L 1.453125 -4.375 L 1.453125 -3.703125 C 1.597656 -3.960938 1.789062 -4.15625 2.03125 -4.28125 C 2.28125 -4.414062 2.578125 -4.484375 2.921875 -4.484375 C 2.972656 -4.484375 3.023438 -4.476562 3.078125 -4.46875 C 3.140625 -4.46875 3.207031 -4.457031 3.28125 -4.4375 Z M 3.296875 -3.703125 "/>
|
||||||
|
</symbol>
|
||||||
|
<symbol overflow="visible" id="glyph1-10">
|
||||||
|
<path style="stroke:none;" d="M 0.75 -4.375 L 1.46875 -4.375 L 1.46875 0 L 0.75 0 Z M 0.75 -6.078125 L 1.46875 -6.078125 L 1.46875 -5.171875 L 0.75 -5.171875 Z M 0.75 -6.078125 "/>
|
||||||
|
</symbol>
|
||||||
|
<symbol overflow="visible" id="glyph1-11">
|
||||||
<path style="stroke:none;" d="M 4.390625 -2.640625 L 4.390625 0 L 3.671875 0 L 3.671875 -2.625 C 3.671875 -3.03125 3.585938 -3.335938 3.421875 -3.546875 C 3.265625 -3.753906 3.023438 -3.859375 2.703125 -3.859375 C 2.316406 -3.859375 2.007812 -3.734375 1.78125 -3.484375 C 1.5625 -3.234375 1.453125 -2.894531 1.453125 -2.46875 L 1.453125 0 L 0.734375 0 L 0.734375 -4.375 L 1.453125 -4.375 L 1.453125 -3.703125 C 1.617188 -3.960938 1.816406 -4.15625 2.046875 -4.28125 C 2.285156 -4.414062 2.554688 -4.484375 2.859375 -4.484375 C 3.367188 -4.484375 3.75 -4.328125 4 -4.015625 C 4.257812 -3.703125 4.390625 -3.242188 4.390625 -2.640625 Z M 4.390625 -2.640625 "/>
|
<path style="stroke:none;" d="M 4.390625 -2.640625 L 4.390625 0 L 3.671875 0 L 3.671875 -2.625 C 3.671875 -3.03125 3.585938 -3.335938 3.421875 -3.546875 C 3.265625 -3.753906 3.023438 -3.859375 2.703125 -3.859375 C 2.316406 -3.859375 2.007812 -3.734375 1.78125 -3.484375 C 1.5625 -3.234375 1.453125 -2.894531 1.453125 -2.46875 L 1.453125 0 L 0.734375 0 L 0.734375 -4.375 L 1.453125 -4.375 L 1.453125 -3.703125 C 1.617188 -3.960938 1.816406 -4.15625 2.046875 -4.28125 C 2.285156 -4.414062 2.554688 -4.484375 2.859375 -4.484375 C 3.367188 -4.484375 3.75 -4.328125 4 -4.015625 C 4.257812 -3.703125 4.390625 -3.242188 4.390625 -2.640625 Z M 4.390625 -2.640625 "/>
|
||||||
</symbol>
|
</symbol>
|
||||||
<symbol overflow="visible" id="glyph1-22">
|
<symbol overflow="visible" id="glyph1-12">
|
||||||
<path style="stroke:none;" d="M 0.9375 -4.140625 L 1.765625 -4.140625 L 1.765625 -3.140625 L 0.9375 -3.140625 Z M 0.9375 -1 L 1.765625 -1 L 1.765625 -0.328125 L 1.125 0.9375 L 0.625 0.9375 L 0.9375 -0.328125 Z M 0.9375 -1 "/>
|
<path style="stroke:none;" d="M 3.640625 -2.234375 C 3.640625 -2.753906 3.53125 -3.15625 3.3125 -3.4375 C 3.09375 -3.726562 2.789062 -3.875 2.40625 -3.875 C 2.019531 -3.875 1.71875 -3.726562 1.5 -3.4375 C 1.289062 -3.15625 1.1875 -2.753906 1.1875 -2.234375 C 1.1875 -1.722656 1.289062 -1.320312 1.5 -1.03125 C 1.71875 -0.75 2.019531 -0.609375 2.40625 -0.609375 C 2.789062 -0.609375 3.09375 -0.75 3.3125 -1.03125 C 3.53125 -1.320312 3.640625 -1.722656 3.640625 -2.234375 Z M 4.359375 -0.546875 C 4.359375 0.203125 4.191406 0.757812 3.859375 1.125 C 3.523438 1.488281 3.019531 1.671875 2.34375 1.671875 C 2.082031 1.671875 1.835938 1.648438 1.609375 1.609375 C 1.390625 1.566406 1.175781 1.507812 0.96875 1.4375 L 0.96875 0.734375 C 1.175781 0.847656 1.382812 0.929688 1.59375 0.984375 C 1.800781 1.046875 2.007812 1.078125 2.21875 1.078125 C 2.695312 1.078125 3.050781 0.953125 3.28125 0.703125 C 3.519531 0.453125 3.640625 0.078125 3.640625 -0.421875 L 3.640625 -0.765625 C 3.484375 -0.515625 3.289062 -0.320312 3.0625 -0.1875 C 2.832031 -0.0625 2.554688 0 2.234375 0 C 1.691406 0 1.253906 -0.203125 0.921875 -0.609375 C 0.597656 -1.023438 0.4375 -1.566406 0.4375 -2.234375 C 0.4375 -2.910156 0.597656 -3.453125 0.921875 -3.859375 C 1.253906 -4.273438 1.691406 -4.484375 2.234375 -4.484375 C 2.554688 -4.484375 2.832031 -4.414062 3.0625 -4.28125 C 3.289062 -4.15625 3.484375 -3.96875 3.640625 -3.71875 L 3.640625 -4.375 L 4.359375 -4.375 Z M 4.359375 -0.546875 "/>
|
||||||
</symbol>
|
</symbol>
|
||||||
<symbol overflow="visible" id="glyph1-23">
|
<symbol overflow="visible" id="glyph1-13">
|
||||||
<path style="stroke:none;" d="M 1.453125 -0.65625 L 1.453125 1.671875 L 0.734375 1.671875 L 0.734375 -4.375 L 1.453125 -4.375 L 1.453125 -3.71875 C 1.597656 -3.976562 1.785156 -4.171875 2.015625 -4.296875 C 2.253906 -4.421875 2.53125 -4.484375 2.84375 -4.484375 C 3.375 -4.484375 3.804688 -4.269531 4.140625 -3.84375 C 4.472656 -3.425781 4.640625 -2.875 4.640625 -2.1875 C 4.640625 -1.5 4.472656 -0.941406 4.140625 -0.515625 C 3.804688 -0.0976562 3.375 0.109375 2.84375 0.109375 C 2.53125 0.109375 2.253906 0.046875 2.015625 -0.078125 C 1.785156 -0.203125 1.597656 -0.394531 1.453125 -0.65625 Z M 3.890625 -2.1875 C 3.890625 -2.71875 3.78125 -3.128906 3.5625 -3.421875 C 3.351562 -3.722656 3.054688 -3.875 2.671875 -3.875 C 2.296875 -3.875 2 -3.722656 1.78125 -3.421875 C 1.5625 -3.128906 1.453125 -2.71875 1.453125 -2.1875 C 1.453125 -1.65625 1.5625 -1.238281 1.78125 -0.9375 C 2 -0.632812 2.296875 -0.484375 2.671875 -0.484375 C 3.054688 -0.484375 3.351562 -0.632812 3.5625 -0.9375 C 3.78125 -1.238281 3.890625 -1.65625 3.890625 -2.1875 Z M 3.890625 -2.1875 "/>
|
<path style="stroke:none;" d="M 3.640625 -3.71875 L 3.640625 -6.078125 L 4.359375 -6.078125 L 4.359375 0 L 3.640625 0 L 3.640625 -0.65625 C 3.484375 -0.394531 3.289062 -0.203125 3.0625 -0.078125 C 2.832031 0.046875 2.554688 0.109375 2.234375 0.109375 C 1.703125 0.109375 1.269531 -0.0976562 0.9375 -0.515625 C 0.601562 -0.941406 0.4375 -1.5 0.4375 -2.1875 C 0.4375 -2.875 0.601562 -3.425781 0.9375 -3.84375 C 1.269531 -4.269531 1.703125 -4.484375 2.234375 -4.484375 C 2.554688 -4.484375 2.832031 -4.421875 3.0625 -4.296875 C 3.289062 -4.171875 3.484375 -3.976562 3.640625 -3.71875 Z M 1.1875 -2.1875 C 1.1875 -1.65625 1.296875 -1.238281 1.515625 -0.9375 C 1.734375 -0.632812 2.03125 -0.484375 2.40625 -0.484375 C 2.789062 -0.484375 3.09375 -0.632812 3.3125 -0.9375 C 3.53125 -1.238281 3.640625 -1.65625 3.640625 -2.1875 C 3.640625 -2.71875 3.53125 -3.128906 3.3125 -3.421875 C 3.09375 -3.722656 2.789062 -3.875 2.40625 -3.875 C 2.03125 -3.875 1.734375 -3.722656 1.515625 -3.421875 C 1.296875 -3.128906 1.1875 -2.71875 1.1875 -2.1875 Z M 1.1875 -2.1875 "/>
|
||||||
</symbol>
|
</symbol>
|
||||||
<symbol overflow="visible" id="glyph1-24">
|
<symbol overflow="visible" id="glyph1-14">
|
||||||
<path style="stroke:none;" d="M 0.390625 -2.515625 L 2.5 -2.515625 L 2.5 -1.875 L 0.390625 -1.875 Z M 0.390625 -2.515625 "/>
|
<path style="stroke:none;" d="M 4.5 -2.375 L 4.5 -2.015625 L 1.1875 -2.015625 C 1.21875 -1.523438 1.367188 -1.148438 1.640625 -0.890625 C 1.910156 -0.628906 2.28125 -0.5 2.75 -0.5 C 3.03125 -0.5 3.300781 -0.53125 3.5625 -0.59375 C 3.820312 -0.664062 4.078125 -0.769531 4.328125 -0.90625 L 4.328125 -0.21875 C 4.066406 -0.113281 3.800781 -0.0351562 3.53125 0.015625 C 3.257812 0.078125 2.988281 0.109375 2.71875 0.109375 C 2.019531 0.109375 1.460938 -0.09375 1.046875 -0.5 C 0.640625 -0.90625 0.4375 -1.453125 0.4375 -2.140625 C 0.4375 -2.859375 0.628906 -3.425781 1.015625 -3.84375 C 1.410156 -4.269531 1.9375 -4.484375 2.59375 -4.484375 C 3.175781 -4.484375 3.640625 -4.289062 3.984375 -3.90625 C 4.328125 -3.53125 4.5 -3.019531 4.5 -2.375 Z M 3.78125 -2.578125 C 3.769531 -2.972656 3.65625 -3.285156 3.4375 -3.515625 C 3.226562 -3.753906 2.945312 -3.875 2.59375 -3.875 C 2.195312 -3.875 1.875 -3.757812 1.625 -3.53125 C 1.382812 -3.300781 1.25 -2.984375 1.21875 -2.578125 Z M 3.78125 -2.578125 "/>
|
||||||
</symbol>
|
</symbol>
|
||||||
<symbol overflow="visible" id="glyph1-25">
|
<symbol overflow="visible" id="glyph1-15">
|
||||||
|
<path style="stroke:none;" d="M 1.53125 -0.671875 L 4.296875 -0.671875 L 4.296875 0 L 0.59375 0 L 0.59375 -0.671875 C 0.882812 -0.972656 1.289062 -1.382812 1.8125 -1.90625 C 2.332031 -2.4375 2.65625 -2.773438 2.78125 -2.921875 C 3.039062 -3.203125 3.21875 -3.441406 3.3125 -3.640625 C 3.414062 -3.835938 3.46875 -4.03125 3.46875 -4.21875 C 3.46875 -4.53125 3.359375 -4.785156 3.140625 -4.984375 C 2.921875 -5.179688 2.640625 -5.28125 2.296875 -5.28125 C 2.046875 -5.28125 1.78125 -5.234375 1.5 -5.140625 C 1.226562 -5.054688 0.9375 -4.925781 0.625 -4.75 L 0.625 -5.546875 C 0.945312 -5.679688 1.242188 -5.78125 1.515625 -5.84375 C 1.796875 -5.90625 2.050781 -5.9375 2.28125 -5.9375 C 2.882812 -5.9375 3.363281 -5.785156 3.71875 -5.484375 C 4.082031 -5.179688 4.265625 -4.78125 4.265625 -4.28125 C 4.265625 -4.039062 4.21875 -3.8125 4.125 -3.59375 C 4.03125 -3.375 3.867188 -3.117188 3.640625 -2.828125 C 3.566406 -2.753906 3.351562 -2.535156 3 -2.171875 C 2.65625 -1.816406 2.164062 -1.316406 1.53125 -0.671875 Z M 1.53125 -0.671875 "/>
|
||||||
|
</symbol>
|
||||||
|
<symbol overflow="visible" id="glyph1-16">
|
||||||
|
<path style="stroke:none;" d="M 3.25 -3.140625 C 3.625 -3.066406 3.914062 -2.898438 4.125 -2.640625 C 4.34375 -2.390625 4.453125 -2.078125 4.453125 -1.703125 C 4.453125 -1.117188 4.253906 -0.671875 3.859375 -0.359375 C 3.460938 -0.046875 2.898438 0.109375 2.171875 0.109375 C 1.921875 0.109375 1.664062 0.0820312 1.40625 0.03125 C 1.15625 -0.0078125 0.890625 -0.078125 0.609375 -0.171875 L 0.609375 -0.9375 C 0.828125 -0.8125 1.066406 -0.710938 1.328125 -0.640625 C 1.585938 -0.578125 1.859375 -0.546875 2.140625 -0.546875 C 2.640625 -0.546875 3.019531 -0.644531 3.28125 -0.84375 C 3.539062 -1.039062 3.671875 -1.328125 3.671875 -1.703125 C 3.671875 -2.046875 3.546875 -2.3125 3.296875 -2.5 C 3.054688 -2.695312 2.722656 -2.796875 2.296875 -2.796875 L 1.625 -2.796875 L 1.625 -3.4375 L 2.328125 -3.4375 C 2.710938 -3.4375 3.007812 -3.515625 3.21875 -3.671875 C 3.425781 -3.828125 3.53125 -4.050781 3.53125 -4.34375 C 3.53125 -4.644531 3.421875 -4.875 3.203125 -5.03125 C 2.992188 -5.195312 2.691406 -5.28125 2.296875 -5.28125 C 2.078125 -5.28125 1.84375 -5.253906 1.59375 -5.203125 C 1.351562 -5.160156 1.082031 -5.085938 0.78125 -4.984375 L 0.78125 -5.6875 C 1.082031 -5.769531 1.363281 -5.832031 1.625 -5.875 C 1.882812 -5.914062 2.132812 -5.9375 2.375 -5.9375 C 2.96875 -5.9375 3.4375 -5.800781 3.78125 -5.53125 C 4.132812 -5.257812 4.3125 -4.890625 4.3125 -4.421875 C 4.3125 -4.097656 4.21875 -3.828125 4.03125 -3.609375 C 3.851562 -3.390625 3.59375 -3.234375 3.25 -3.140625 Z M 3.25 -3.140625 "/>
|
||||||
|
</symbol>
|
||||||
|
<symbol overflow="visible" id="glyph1-17">
|
||||||
|
<path style="stroke:none;" d="M 2.734375 -5.0625 L 1.671875 -2.15625 L 3.8125 -2.15625 Z M 2.296875 -5.828125 L 3.1875 -5.828125 L 5.40625 0 L 4.59375 0 L 4.0625 -1.5 L 1.421875 -1.5 L 0.890625 0 L 0.0625 0 Z M 2.296875 -5.828125 "/>
|
||||||
|
</symbol>
|
||||||
|
<symbol overflow="visible" id="glyph1-18">
|
||||||
<path style="stroke:none;" d="M 0.75 -6.078125 L 1.46875 -6.078125 L 1.46875 0 L 0.75 0 Z M 0.75 -6.078125 "/>
|
<path style="stroke:none;" d="M 0.75 -6.078125 L 1.46875 -6.078125 L 1.46875 0 L 0.75 0 Z M 0.75 -6.078125 "/>
|
||||||
</symbol>
|
</symbol>
|
||||||
<symbol overflow="visible" id="glyph1-26">
|
<symbol overflow="visible" id="glyph1-19">
|
||||||
<path style="stroke:none;" d="M 0.234375 -4.375 L 1 -4.375 L 2.375 -0.703125 L 3.734375 -4.375 L 4.5 -4.375 L 2.859375 0 L 1.875 0 Z M 0.234375 -4.375 "/>
|
<path style="stroke:none;" d="M 3.90625 -4.203125 L 3.90625 -3.53125 C 3.695312 -3.644531 3.488281 -3.726562 3.28125 -3.78125 C 3.082031 -3.84375 2.878906 -3.875 2.671875 -3.875 C 2.203125 -3.875 1.835938 -3.722656 1.578125 -3.421875 C 1.328125 -3.128906 1.203125 -2.71875 1.203125 -2.1875 C 1.203125 -1.65625 1.328125 -1.238281 1.578125 -0.9375 C 1.835938 -0.644531 2.203125 -0.5 2.671875 -0.5 C 2.878906 -0.5 3.082031 -0.523438 3.28125 -0.578125 C 3.488281 -0.640625 3.695312 -0.722656 3.90625 -0.828125 L 3.90625 -0.171875 C 3.707031 -0.078125 3.5 -0.0078125 3.28125 0.03125 C 3.0625 0.0820312 2.832031 0.109375 2.59375 0.109375 C 1.9375 0.109375 1.410156 -0.09375 1.015625 -0.5 C 0.628906 -0.914062 0.4375 -1.476562 0.4375 -2.1875 C 0.4375 -2.894531 0.632812 -3.453125 1.03125 -3.859375 C 1.425781 -4.273438 1.960938 -4.484375 2.640625 -4.484375 C 2.859375 -4.484375 3.070312 -4.457031 3.28125 -4.40625 C 3.5 -4.363281 3.707031 -4.296875 3.90625 -4.203125 Z M 3.90625 -4.203125 "/>
|
||||||
</symbol>
|
</symbol>
|
||||||
<symbol overflow="visible" id="glyph1-27">
|
<symbol overflow="visible" id="glyph1-20">
|
||||||
|
<path style="stroke:none;" d="M 4.390625 -2.640625 L 4.390625 0 L 3.671875 0 L 3.671875 -2.625 C 3.671875 -3.03125 3.585938 -3.335938 3.421875 -3.546875 C 3.265625 -3.753906 3.023438 -3.859375 2.703125 -3.859375 C 2.316406 -3.859375 2.007812 -3.734375 1.78125 -3.484375 C 1.5625 -3.234375 1.453125 -2.894531 1.453125 -2.46875 L 1.453125 0 L 0.734375 0 L 0.734375 -6.078125 L 1.453125 -6.078125 L 1.453125 -3.703125 C 1.617188 -3.960938 1.816406 -4.15625 2.046875 -4.28125 C 2.285156 -4.414062 2.554688 -4.484375 2.859375 -4.484375 C 3.367188 -4.484375 3.75 -4.328125 4 -4.015625 C 4.257812 -3.703125 4.390625 -3.242188 4.390625 -2.640625 Z M 4.390625 -2.640625 "/>
|
||||||
|
</symbol>
|
||||||
|
<symbol overflow="visible" id="glyph1-21">
|
||||||
|
<path style="stroke:none;" d="M 2.96875 -6.078125 L 2.96875 -5.484375 L 2.28125 -5.484375 C 2.019531 -5.484375 1.835938 -5.429688 1.734375 -5.328125 C 1.640625 -5.222656 1.59375 -5.035156 1.59375 -4.765625 L 1.59375 -4.375 L 2.78125 -4.375 L 2.78125 -3.8125 L 1.59375 -3.8125 L 1.59375 0 L 0.875 0 L 0.875 -3.8125 L 0.1875 -3.8125 L 0.1875 -4.375 L 0.875 -4.375 L 0.875 -4.6875 C 0.875 -5.164062 0.984375 -5.515625 1.203125 -5.734375 C 1.429688 -5.960938 1.796875 -6.078125 2.296875 -6.078125 Z M 2.96875 -6.078125 "/>
|
||||||
|
</symbol>
|
||||||
|
<symbol overflow="visible" id="glyph1-22">
|
||||||
|
<path style="stroke:none;" d="M 0.734375 -6.078125 L 1.453125 -6.078125 L 1.453125 -2.484375 L 3.59375 -4.375 L 4.515625 -4.375 L 2.1875 -2.328125 L 4.609375 0 L 3.671875 0 L 1.453125 -2.140625 L 1.453125 0 L 0.734375 0 Z M 0.734375 -6.078125 "/>
|
||||||
|
</symbol>
|
||||||
|
<symbol overflow="visible" id="glyph1-23">
|
||||||
<path style="stroke:none;" d="M 0.34375 -4.375 L 1.0625 -4.375 L 1.953125 -0.96875 L 2.84375 -4.375 L 3.703125 -4.375 L 4.59375 -0.96875 L 5.484375 -4.375 L 6.203125 -4.375 L 5.0625 0 L 4.21875 0 L 3.28125 -3.59375 L 2.328125 0 L 1.484375 0 Z M 0.34375 -4.375 "/>
|
<path style="stroke:none;" d="M 0.34375 -4.375 L 1.0625 -4.375 L 1.953125 -0.96875 L 2.84375 -4.375 L 3.703125 -4.375 L 4.59375 -0.96875 L 5.484375 -4.375 L 6.203125 -4.375 L 5.0625 0 L 4.21875 0 L 3.28125 -3.59375 L 2.328125 0 L 1.484375 0 Z M 0.34375 -4.375 "/>
|
||||||
</symbol>
|
</symbol>
|
||||||
|
<symbol overflow="visible" id="glyph1-24">
|
||||||
|
<path style="stroke:none;" d="M 4.28125 -5.640625 L 4.28125 -4.875 C 3.976562 -5.019531 3.691406 -5.125 3.421875 -5.1875 C 3.160156 -5.257812 2.910156 -5.296875 2.671875 -5.296875 C 2.234375 -5.296875 1.898438 -5.210938 1.671875 -5.046875 C 1.441406 -4.878906 1.328125 -4.644531 1.328125 -4.34375 C 1.328125 -4.082031 1.398438 -3.882812 1.546875 -3.75 C 1.703125 -3.625 2 -3.519531 2.4375 -3.4375 L 2.90625 -3.34375 C 3.5 -3.226562 3.9375 -3.03125 4.21875 -2.75 C 4.5 -2.46875 4.640625 -2.085938 4.640625 -1.609375 C 4.640625 -1.046875 4.445312 -0.617188 4.0625 -0.328125 C 3.6875 -0.0351562 3.132812 0.109375 2.40625 0.109375 C 2.125 0.109375 1.828125 0.078125 1.515625 0.015625 C 1.203125 -0.046875 0.878906 -0.140625 0.546875 -0.265625 L 0.546875 -1.078125 C 0.867188 -0.890625 1.179688 -0.75 1.484375 -0.65625 C 1.796875 -0.570312 2.101562 -0.53125 2.40625 -0.53125 C 2.851562 -0.53125 3.195312 -0.617188 3.4375 -0.796875 C 3.6875 -0.972656 3.8125 -1.222656 3.8125 -1.546875 C 3.8125 -1.835938 3.722656 -2.0625 3.546875 -2.21875 C 3.367188 -2.382812 3.082031 -2.507812 2.6875 -2.59375 L 2.203125 -2.6875 C 1.609375 -2.800781 1.179688 -2.984375 0.921875 -3.234375 C 0.660156 -3.484375 0.53125 -3.832031 0.53125 -4.28125 C 0.53125 -4.789062 0.710938 -5.191406 1.078125 -5.484375 C 1.441406 -5.785156 1.941406 -5.9375 2.578125 -5.9375 C 2.847656 -5.9375 3.125 -5.910156 3.40625 -5.859375 C 3.695312 -5.816406 3.988281 -5.742188 4.28125 -5.640625 Z M 4.28125 -5.640625 "/>
|
||||||
|
</symbol>
|
||||||
</g>
|
</g>
|
||||||
<clipPath id="clip1">
|
<clipPath id="clip1">
|
||||||
<path d="M 683.339844 48 L 725 48 L 725 59 L 683.339844 59 Z M 683.339844 48 "/>
|
<path d="M 1149.457031 48 L 1191 48 L 1191 59 L 1149.457031 59 Z M 1149.457031 48 "/>
|
||||||
</clipPath>
|
</clipPath>
|
||||||
<clipPath id="clip2">
|
<clipPath id="clip2">
|
||||||
<path d="M 812.351562 48 L 847.65625 48 L 847.65625 59 L 812.351562 59 Z M 812.351562 48 "/>
|
<path d="M 168.484375 80 L 210 80 L 210 91 L 168.484375 91 Z M 168.484375 80 "/>
|
||||||
</clipPath>
|
</clipPath>
|
||||||
<clipPath id="clip3">
|
<clipPath id="clip3">
|
||||||
<path d="M 1068.0625 48 L 1099.449219 48 L 1099.449219 59 L 1068.0625 59 Z M 1068.0625 48 "/>
|
<path d="M 945.597656 80 L 987 80 L 987 91 L 945.597656 91 Z M 945.597656 80 "/>
|
||||||
</clipPath>
|
</clipPath>
|
||||||
<clipPath id="clip4">
|
<clipPath id="clip4">
|
||||||
<path d="M 865.34375 80 L 898 80 L 898 91 L 865.34375 91 Z M 865.34375 80 "/>
|
<path d="M 250.011719 69 L 303 69 L 303 78 L 250.011719 78 Z M 250.011719 69 "/>
|
||||||
</clipPath>
|
</clipPath>
|
||||||
<clipPath id="clip5">
|
<clipPath id="clip5">
|
||||||
<path d="M 951.027344 80 L 981.15625 80 L 981.15625 91 L 951.027344 91 Z M 951.027344 80 "/>
|
<path d="M 979.003906 69 L 1003.683594 69 L 1003.683594 77 L 979.003906 77 Z M 979.003906 69 "/>
|
||||||
</clipPath>
|
</clipPath>
|
||||||
<clipPath id="clip6">
|
<clipPath id="clip6">
|
||||||
<path d="M 764.328125 112 L 801.253906 112 L 801.253906 123 L 764.328125 123 Z M 764.328125 112 "/>
|
<path d="M 1018.117188 112 L 1060 112 L 1060 123 L 1018.117188 123 Z M 1018.117188 112 "/>
|
||||||
</clipPath>
|
</clipPath>
|
||||||
<clipPath id="clip7">
|
<clipPath id="clip7">
|
||||||
<path d="M 910 112 L 939.957031 112 L 939.957031 123 L 910 123 Z M 910 112 "/>
|
<path d="M 583.375 101 L 637 101 L 637 110 L 583.375 110 Z M 583.375 101 "/>
|
||||||
</clipPath>
|
</clipPath>
|
||||||
<clipPath id="clip8">
|
<clipPath id="clip8">
|
||||||
<path d="M 1007.089844 112 L 1022.230469 112 L 1022.230469 123 L 1007.089844 123 Z M 1007.089844 112 "/>
|
<path d="M 1049.300781 101 L 1070.394531 101 L 1070.394531 109 L 1049.300781 109 Z M 1049.300781 101 "/>
|
||||||
</clipPath>
|
</clipPath>
|
||||||
<clipPath id="clip9">
|
<clipPath id="clip9">
|
||||||
<path d="M 789.792969 101 L 809 101 L 809 110 L 789.792969 110 Z M 789.792969 101 "/>
|
<path d="M 1082.304688 144 L 1124 144 L 1124 155 L 1082.304688 155 Z M 1082.304688 144 "/>
|
||||||
</clipPath>
|
</clipPath>
|
||||||
<clipPath id="clip10">
|
<clipPath id="clip10">
|
||||||
<path d="M 931.160156 101 L 950 101 L 950 110 L 931.160156 110 Z M 931.160156 101 "/>
|
<path d="M 819.433594 133 L 873 133 L 873 142 L 819.433594 142 Z M 819.433594 133 "/>
|
||||||
</clipPath>
|
</clipPath>
|
||||||
<clipPath id="clip11">
|
<clipPath id="clip11">
|
||||||
<path d="M 1013.980469 101 L 1033 101 L 1033 110 L 1013.980469 110 Z M 1013.980469 101 "/>
|
<path d="M 1112 133 L 1132.316406 133 L 1132.316406 141 L 1112 141 Z M 1112 133 "/>
|
||||||
</clipPath>
|
</clipPath>
|
||||||
<clipPath id="clip12">
|
<clipPath id="clip12">
|
||||||
<path d="M 836.167969 37 L 1028 37 L 1028 46 L 836.167969 46 Z M 836.167969 37 "/>
|
<path d="M 901.039062 37 L 985 37 L 985 45 L 901.039062 45 Z M 901.039062 37 "/>
|
||||||
</clipPath>
|
</clipPath>
|
||||||
<clipPath id="clip13">
|
<clipPath id="clip13">
|
||||||
<path d="M 1088.320312 37 L 1158 37 L 1158 45 L 1088.320312 45 Z M 1088.320312 37 "/>
|
<path d="M 1179.296875 37 L 1200.945312 37 L 1200.945312 45 L 1179.296875 45 Z M 1179.296875 37 "/>
|
||||||
</clipPath>
|
</clipPath>
|
||||||
</defs>
|
</defs>
|
||||||
<g id="surface2">
|
<g id="surface2">
|
||||||
<rect x="0" y="0" width="1280" height="152" style="fill:rgb(90%,90%,90%);fill-opacity:1;stroke:none;"/>
|
<rect x="0" y="0" width="1280" height="184" style="fill:rgb(90%,90%,90%);fill-opacity:1;stroke:none;"/>
|
||||||
<path style="fill:none;stroke-width:1;stroke-linecap:butt;stroke-linejoin:miter;stroke:rgb(70%,70%,70%);stroke-opacity:1;stroke-miterlimit:10;" d="M 4 0 L 4 152 "/>
|
<path style="fill:none;stroke-width:1;stroke-linecap:butt;stroke-linejoin:miter;stroke:rgb(70%,70%,70%);stroke-opacity:1;stroke-miterlimit:10;" d="M 4 0 L 4 184 "/>
|
||||||
<path style="fill:none;stroke-width:1;stroke-linecap:butt;stroke-linejoin:miter;stroke:rgb(70%,70%,70%);stroke-opacity:1;stroke-miterlimit:10;" d="M 155.40625 0 L 155.40625 152 "/>
|
<path style="fill:none;stroke-width:1;stroke-linecap:butt;stroke-linejoin:miter;stroke:rgb(70%,70%,70%);stroke-opacity:1;stroke-miterlimit:10;" d="M 195.652344 0 L 195.652344 184 "/>
|
||||||
<path style="fill:none;stroke-width:1;stroke-linecap:butt;stroke-linejoin:miter;stroke:rgb(70%,70%,70%);stroke-opacity:1;stroke-miterlimit:10;" d="M 306.808594 0 L 306.808594 152 "/>
|
<path style="fill:none;stroke-width:1;stroke-linecap:butt;stroke-linejoin:miter;stroke:rgb(70%,70%,70%);stroke-opacity:1;stroke-miterlimit:10;" d="M 387.304688 0 L 387.304688 184 "/>
|
||||||
<path style="fill:none;stroke-width:1;stroke-linecap:butt;stroke-linejoin:miter;stroke:rgb(70%,70%,70%);stroke-opacity:1;stroke-miterlimit:10;" d="M 458.214844 0 L 458.214844 152 "/>
|
<path style="fill:none;stroke-width:1;stroke-linecap:butt;stroke-linejoin:miter;stroke:rgb(70%,70%,70%);stroke-opacity:1;stroke-miterlimit:10;" d="M 578.957031 0 L 578.957031 184 "/>
|
||||||
<path style="fill:none;stroke-width:1;stroke-linecap:butt;stroke-linejoin:miter;stroke:rgb(70%,70%,70%);stroke-opacity:1;stroke-miterlimit:10;" d="M 609.621094 0 L 609.621094 152 "/>
|
<path style="fill:none;stroke-width:1;stroke-linecap:butt;stroke-linejoin:miter;stroke:rgb(70%,70%,70%);stroke-opacity:1;stroke-miterlimit:10;" d="M 770.613281 0 L 770.613281 184 "/>
|
||||||
<path style="fill:none;stroke-width:1;stroke-linecap:butt;stroke-linejoin:miter;stroke:rgb(70%,70%,70%);stroke-opacity:1;stroke-miterlimit:10;" d="M 761.027344 0 L 761.027344 152 "/>
|
<path style="fill:none;stroke-width:1;stroke-linecap:butt;stroke-linejoin:miter;stroke:rgb(70%,70%,70%);stroke-opacity:1;stroke-miterlimit:10;" d="M 962.265625 0 L 962.265625 184 "/>
|
||||||
<path style="fill:none;stroke-width:1;stroke-linecap:butt;stroke-linejoin:miter;stroke:rgb(70%,70%,70%);stroke-opacity:1;stroke-miterlimit:10;" d="M 912.429688 0 L 912.429688 152 "/>
|
<path style="fill:none;stroke-width:1;stroke-linecap:butt;stroke-linejoin:miter;stroke:rgb(70%,70%,70%);stroke-opacity:1;stroke-miterlimit:10;" d="M 1153.917969 0 L 1153.917969 184 "/>
|
||||||
<path style="fill:none;stroke-width:1;stroke-linecap:butt;stroke-linejoin:miter;stroke:rgb(70%,70%,70%);stroke-opacity:1;stroke-miterlimit:10;" d="M 1063.835938 0 L 1063.835938 152 "/>
|
|
||||||
<path style="fill:none;stroke-width:1;stroke-linecap:butt;stroke-linejoin:miter;stroke:rgb(70%,70%,70%);stroke-opacity:1;stroke-miterlimit:10;" d="M 1215.242188 0 L 1215.242188 152 "/>
|
|
||||||
<g style="fill:rgb(40%,40%,40%);fill-opacity:1;">
|
<g style="fill:rgb(40%,40%,40%);fill-opacity:1;">
|
||||||
<use xlink:href="#glyph0-1" x="4" y="147.503906"/>
|
<use xlink:href="#glyph0-1" x="4" y="179.503906"/>
|
||||||
<use xlink:href="#glyph0-2" x="11.582031" y="147.503906"/>
|
<use xlink:href="#glyph0-2" x="11.582031" y="179.503906"/>
|
||||||
<use xlink:href="#glyph0-3" x="18.935547" y="147.503906"/>
|
<use xlink:href="#glyph0-3" x="18.935547" y="179.503906"/>
|
||||||
<use xlink:href="#glyph0-4" x="25.533203" y="147.503906"/>
|
<use xlink:href="#glyph0-4" x="25.533203" y="179.503906"/>
|
||||||
<use xlink:href="#glyph0-5" x="33.138672" y="147.503906"/>
|
<use xlink:href="#glyph0-5" x="33.138672" y="179.503906"/>
|
||||||
<use xlink:href="#glyph0-6" x="36.953125" y="147.503906"/>
|
<use xlink:href="#glyph0-6" x="36.953125" y="179.503906"/>
|
||||||
<use xlink:href="#glyph0-7" x="44.570312" y="147.503906"/>
|
<use xlink:href="#glyph0-7" x="44.570312" y="179.503906"/>
|
||||||
<use xlink:href="#glyph0-8" x="49.503906" y="147.503906"/>
|
<use xlink:href="#glyph0-8" x="49.503906" y="179.503906"/>
|
||||||
<use xlink:href="#glyph0-9" x="52.837891" y="147.503906"/>
|
<use xlink:href="#glyph0-9" x="52.837891" y="179.503906"/>
|
||||||
<use xlink:href="#glyph0-5" x="60.455078" y="147.503906"/>
|
<use xlink:href="#glyph0-5" x="60.455078" y="179.503906"/>
|
||||||
<use xlink:href="#glyph0-9" x="64.269531" y="147.503906"/>
|
<use xlink:href="#glyph0-9" x="64.269531" y="179.503906"/>
|
||||||
<use xlink:href="#glyph0-8" x="71.886719" y="147.503906"/>
|
<use xlink:href="#glyph0-8" x="71.886719" y="179.503906"/>
|
||||||
<use xlink:href="#glyph0-10" x="75.220703" y="147.503906"/>
|
<use xlink:href="#glyph0-10" x="75.220703" y="179.503906"/>
|
||||||
<use xlink:href="#glyph0-8" x="82.322266" y="147.503906"/>
|
<use xlink:href="#glyph0-8" x="82.322266" y="179.503906"/>
|
||||||
<use xlink:href="#glyph0-11" x="85.65625" y="147.503906"/>
|
<use xlink:href="#glyph0-11" x="85.65625" y="179.503906"/>
|
||||||
<use xlink:href="#glyph0-8" x="91.908203" y="147.503906"/>
|
<use xlink:href="#glyph0-8" x="91.908203" y="179.503906"/>
|
||||||
<use xlink:href="#glyph0-12" x="95.242188" y="147.503906"/>
|
<use xlink:href="#glyph0-12" x="95.242188" y="179.503906"/>
|
||||||
<use xlink:href="#glyph0-13" x="102.583984" y="147.503906"/>
|
<use xlink:href="#glyph0-13" x="102.583984" y="179.503906"/>
|
||||||
<use xlink:href="#glyph0-14" x="110.189453" y="147.503906"/>
|
<use xlink:href="#glyph0-14" x="110.189453" y="179.503906"/>
|
||||||
<use xlink:href="#glyph0-5" x="114.232422" y="147.503906"/>
|
<use xlink:href="#glyph0-5" x="114.232422" y="179.503906"/>
|
||||||
<use xlink:href="#glyph0-15" x="118.046875" y="147.503906"/>
|
<use xlink:href="#glyph0-15" x="118.046875" y="179.503906"/>
|
||||||
<use xlink:href="#glyph0-16" x="125.681641" y="147.503906"/>
|
<use xlink:href="#glyph0-16" x="125.681641" y="179.503906"/>
|
||||||
<use xlink:href="#glyph0-5" x="133.316406" y="147.503906"/>
|
<use xlink:href="#glyph0-5" x="133.316406" y="179.503906"/>
|
||||||
<use xlink:href="#glyph0-17" x="137.130859" y="147.503906"/>
|
<use xlink:href="#glyph0-17" x="137.130859" y="179.503906"/>
|
||||||
<use xlink:href="#glyph0-11" x="144.736328" y="147.503906"/>
|
<use xlink:href="#glyph0-11" x="144.736328" y="179.503906"/>
|
||||||
</g>
|
</g>
|
||||||
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,80%,40%);fill-opacity:1;" d="M 11.480469 46 L 18.324219 46 L 18.324219 60 L 11.480469 60 Z M 11.480469 46 "/>
|
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,80%,40%);fill-opacity:1;" d="M 10.746094 46 L 18.640625 46 L 18.640625 60 L 10.746094 60 Z M 10.746094 46 "/>
|
||||||
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,80%,40%);fill-opacity:1;" d="M 18.324219 46 L 93.210938 46 L 93.210938 60 L 18.324219 60 Z M 18.324219 46 "/>
|
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,80%,40%);fill-opacity:1;" d="M 18.640625 46 L 59.882812 46 L 59.882812 60 L 18.640625 60 Z M 18.640625 46 "/>
|
||||||
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,40%,40%);fill-opacity:1;" d="M 93.207031 46 L 671.605469 46 L 671.605469 60 L 93.207031 60 Z M 93.207031 46 "/>
|
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,40%,40%);fill-opacity:1;" d="M 59.886719 46 L 491.21875 46 L 491.21875 60 L 59.886719 60 Z M 59.886719 46 "/>
|
||||||
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,80%,40%);fill-opacity:1;" d="M 671.605469 46 L 681.339844 46 L 681.339844 60 L 671.605469 60 Z M 671.605469 46 "/>
|
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,80%,40%);fill-opacity:1;" d="M 491.21875 46 L 523.03125 46 L 523.03125 60 L 491.21875 60 Z M 491.21875 46 "/>
|
||||||
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(50%,90%,50%);fill-opacity:1;" d="M 681.339844 46 L 732.652344 46 L 732.652344 60 L 681.339844 60 Z M 681.339844 46 "/>
|
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,40%,40%);fill-opacity:1;" d="M 523.035156 46 L 618.25 46 L 618.25 60 L 523.035156 60 Z M 523.035156 46 "/>
|
||||||
|
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,80%,40%);fill-opacity:1;" d="M 618.246094 46 L 621.214844 46 L 621.214844 60 L 618.246094 60 Z M 618.246094 46 "/>
|
||||||
|
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,40%,40%);fill-opacity:1;" d="M 621.21875 46 L 864.0625 46 L 864.0625 60 L 621.21875 60 Z M 621.21875 46 "/>
|
||||||
|
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,80%,40%);fill-opacity:1;" d="M 864.0625 46 L 871 46 L 871 60 L 864.0625 60 Z M 864.0625 46 "/>
|
||||||
|
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(50%,90%,50%);fill-opacity:1;" d="M 871 46 L 918.414062 46 L 918.414062 60 L 871 60 Z M 871 46 "/>
|
||||||
|
<g style="fill:rgb(0%,0%,0%);fill-opacity:1;">
|
||||||
|
<use xlink:href="#glyph0-18" x="873" y="58"/>
|
||||||
|
<use xlink:href="#glyph0-7" x="877.705078" y="58"/>
|
||||||
|
<use xlink:href="#glyph0-2" x="882.638672" y="58"/>
|
||||||
|
<use xlink:href="#glyph0-3" x="889.992188" y="58"/>
|
||||||
|
<use xlink:href="#glyph0-19" x="896.589844" y="58"/>
|
||||||
|
<use xlink:href="#glyph0-20" x="903.972656" y="58"/>
|
||||||
|
<use xlink:href="#glyph0-13" x="907.306641" y="58"/>
|
||||||
|
</g>
|
||||||
|
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,80%,40%);fill-opacity:1;" d="M 918.414062 46 L 927.882812 46 L 927.882812 60 L 918.414062 60 Z M 918.414062 46 "/>
|
||||||
|
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,40%,40%);fill-opacity:1;" d="M 927.882812 46 L 1134.214844 46 L 1134.214844 60 L 927.882812 60 Z M 927.882812 46 "/>
|
||||||
|
<g style="fill:rgb(100%,100%,100%);fill-opacity:1;">
|
||||||
|
<use xlink:href="#glyph0-21" x="929.882812" y="58"/>
|
||||||
|
<use xlink:href="#glyph0-22" x="937.5" y="58"/>
|
||||||
|
<use xlink:href="#glyph0-8" x="947.314453" y="58"/>
|
||||||
|
<use xlink:href="#glyph0-18" x="950.648438" y="58"/>
|
||||||
|
<use xlink:href="#glyph0-3" x="955.353516" y="58"/>
|
||||||
|
<use xlink:href="#glyph0-4" x="961.951172" y="58"/>
|
||||||
|
<use xlink:href="#glyph0-23" x="969.556641" y="58"/>
|
||||||
|
<use xlink:href="#glyph0-2" x="973.371094" y="58"/>
|
||||||
|
<use xlink:href="#glyph0-22" x="980.724609" y="58"/>
|
||||||
|
<use xlink:href="#glyph0-2" x="990.539062" y="58"/>
|
||||||
|
<use xlink:href="#glyph0-8" x="997.892578" y="58"/>
|
||||||
|
<use xlink:href="#glyph0-18" x="1001.226562" y="58"/>
|
||||||
|
<use xlink:href="#glyph0-24" x="1005.931641" y="58"/>
|
||||||
|
<use xlink:href="#glyph0-8" x="1011.931641" y="58"/>
|
||||||
|
<use xlink:href="#glyph0-9" x="1015.265625" y="58"/>
|
||||||
|
<use xlink:href="#glyph0-20" x="1022.882812" y="58"/>
|
||||||
|
<use xlink:href="#glyph0-19" x="1026.216797" y="58"/>
|
||||||
|
</g>
|
||||||
|
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,80%,40%);fill-opacity:1;" d="M 1134.214844 46 L 1147.457031 46 L 1147.457031 60 L 1134.214844 60 Z M 1134.214844 46 "/>
|
||||||
|
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(50%,90%,50%);fill-opacity:1;" d="M 1147.457031 46 L 1196.730469 46 L 1196.730469 60 L 1147.457031 60 Z M 1147.457031 46 "/>
|
||||||
<g clip-path="url(#clip1)" clip-rule="nonzero">
|
<g clip-path="url(#clip1)" clip-rule="nonzero">
|
||||||
<g style="fill:rgb(0%,0%,0%);fill-opacity:1;">
|
<g style="fill:rgb(0%,0%,0%);fill-opacity:1;">
|
||||||
<use xlink:href="#glyph0-18" x="683.339844" y="58"/>
|
<use xlink:href="#glyph0-18" x="1149.457031" y="58"/>
|
||||||
<use xlink:href="#glyph0-7" x="688.044922" y="58"/>
|
<use xlink:href="#glyph0-7" x="1154.162109" y="58"/>
|
||||||
<use xlink:href="#glyph0-2" x="692.978516" y="58"/>
|
<use xlink:href="#glyph0-2" x="1159.095703" y="58"/>
|
||||||
<use xlink:href="#glyph0-3" x="700.332031" y="58"/>
|
<use xlink:href="#glyph0-3" x="1166.449219" y="58"/>
|
||||||
<use xlink:href="#glyph0-19" x="706.929688" y="58"/>
|
<use xlink:href="#glyph0-19" x="1173.046875" y="58"/>
|
||||||
<use xlink:href="#glyph0-20" x="714.3125" y="58"/>
|
<use xlink:href="#glyph0-20" x="1180.429688" y="58"/>
|
||||||
<use xlink:href="#glyph0-13" x="717.646484" y="58"/>
|
<use xlink:href="#glyph0-13" x="1183.763672" y="58"/>
|
||||||
</g>
|
</g>
|
||||||
</g>
|
</g>
|
||||||
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,80%,40%);fill-opacity:1;" d="M 732.652344 46 L 740.554688 46 L 740.554688 60 L 732.652344 60 Z M 732.652344 46 "/>
|
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,80%,40%);fill-opacity:1;" d="M 1196.730469 46 L 1200.945312 46 L 1200.945312 60 L 1196.730469 60 Z M 1196.730469 46 "/>
|
||||||
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,40%,40%);fill-opacity:1;" d="M 740.554688 46 L 805.128906 46 L 805.128906 60 L 740.554688 60 Z M 740.554688 46 "/>
|
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,80%,40%);fill-opacity:1;" d="M 59.886719 78 L 62.914062 78 L 62.914062 92 L 59.886719 92 Z M 59.886719 78 "/>
|
||||||
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,80%,40%);fill-opacity:1;" d="M 805.128906 46 L 810.351562 46 L 810.351562 60 L 805.128906 60 Z M 805.128906 46 "/>
|
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,80%,40%);fill-opacity:1;" d="M 62.914062 78 L 166.484375 78 L 166.484375 92 L 62.914062 92 Z M 62.914062 78 "/>
|
||||||
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(50%,90%,50%);fill-opacity:1;" d="M 810.351562 46 L 847.65625 46 L 847.65625 60 L 810.351562 60 Z M 810.351562 46 "/>
|
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(50%,90%,50%);fill-opacity:1;" d="M 166.484375 78 L 471.960938 78 L 471.960938 92 L 166.484375 92 Z M 166.484375 78 "/>
|
||||||
<g clip-path="url(#clip2)" clip-rule="nonzero">
|
<g clip-path="url(#clip2)" clip-rule="nonzero">
|
||||||
<g style="fill:rgb(0%,0%,0%);fill-opacity:1;">
|
<g style="fill:rgb(0%,0%,0%);fill-opacity:1;">
|
||||||
<use xlink:href="#glyph0-18" x="812.351562" y="58"/>
|
<use xlink:href="#glyph0-18" x="168.484375" y="90"/>
|
||||||
<use xlink:href="#glyph0-7" x="817.056641" y="58"/>
|
<use xlink:href="#glyph0-7" x="173.189453" y="90"/>
|
||||||
<use xlink:href="#glyph0-2" x="821.990234" y="58"/>
|
<use xlink:href="#glyph0-2" x="178.123047" y="90"/>
|
||||||
<use xlink:href="#glyph0-3" x="829.34375" y="58"/>
|
<use xlink:href="#glyph0-3" x="185.476562" y="90"/>
|
||||||
<use xlink:href="#glyph0-19" x="835.941406" y="58"/>
|
<use xlink:href="#glyph0-19" x="192.074219" y="90"/>
|
||||||
<use xlink:href="#glyph0-20" x="843.324219" y="58"/>
|
<use xlink:href="#glyph0-20" x="199.457031" y="90"/>
|
||||||
<use xlink:href="#glyph0-13" x="846.658203" y="58"/>
|
<use xlink:href="#glyph0-13" x="202.791016" y="90"/>
|
||||||
</g>
|
</g>
|
||||||
</g>
|
</g>
|
||||||
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,80%,40%);fill-opacity:1;" d="M 847.660156 46 L 852.671875 46 L 852.671875 60 L 847.660156 60 Z M 847.660156 46 "/>
|
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,80%,40%);fill-opacity:1;" d="M 471.957031 78 L 483.074219 78 L 483.074219 92 L 471.957031 92 Z M 471.957031 78 "/>
|
||||||
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,40%,40%);fill-opacity:1;" d="M 852.671875 46 L 1053.917969 46 L 1053.917969 60 L 852.671875 60 Z M 852.671875 46 "/>
|
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,40%,40%);fill-opacity:1;" d="M 483.074219 78 L 932.367188 78 L 932.367188 92 L 483.074219 92 Z M 483.074219 78 "/>
|
||||||
<g style="fill:rgb(100%,100%,100%);fill-opacity:1;">
|
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,80%,40%);fill-opacity:1;" d="M 932.367188 78 L 943.597656 78 L 943.597656 92 L 932.367188 92 Z M 932.367188 78 "/>
|
||||||
<use xlink:href="#glyph0-21" x="854.671875" y="58"/>
|
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(50%,90%,50%);fill-opacity:1;" d="M 943.597656 78 L 996.683594 78 L 996.683594 92 L 943.597656 92 Z M 943.597656 78 "/>
|
||||||
<use xlink:href="#glyph0-22" x="862.289062" y="58"/>
|
|
||||||
<use xlink:href="#glyph0-8" x="872.103516" y="58"/>
|
|
||||||
<use xlink:href="#glyph0-18" x="875.4375" y="58"/>
|
|
||||||
<use xlink:href="#glyph0-3" x="880.142578" y="58"/>
|
|
||||||
<use xlink:href="#glyph0-4" x="886.740234" y="58"/>
|
|
||||||
<use xlink:href="#glyph0-23" x="894.345703" y="58"/>
|
|
||||||
<use xlink:href="#glyph0-2" x="898.160156" y="58"/>
|
|
||||||
<use xlink:href="#glyph0-22" x="905.513672" y="58"/>
|
|
||||||
<use xlink:href="#glyph0-2" x="915.328125" y="58"/>
|
|
||||||
<use xlink:href="#glyph0-8" x="922.681641" y="58"/>
|
|
||||||
<use xlink:href="#glyph0-18" x="926.015625" y="58"/>
|
|
||||||
<use xlink:href="#glyph0-24" x="930.720703" y="58"/>
|
|
||||||
<use xlink:href="#glyph0-8" x="936.720703" y="58"/>
|
|
||||||
<use xlink:href="#glyph0-9" x="940.054688" y="58"/>
|
|
||||||
<use xlink:href="#glyph0-20" x="947.671875" y="58"/>
|
|
||||||
<use xlink:href="#glyph0-19" x="951.005859" y="58"/>
|
|
||||||
</g>
|
|
||||||
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,80%,40%);fill-opacity:1;" d="M 1053.917969 46 L 1066.0625 46 L 1066.0625 60 L 1053.917969 60 Z M 1053.917969 46 "/>
|
|
||||||
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(50%,90%,50%);fill-opacity:1;" d="M 1066.0625 46 L 1099.449219 46 L 1099.449219 60 L 1066.0625 60 Z M 1066.0625 46 "/>
|
|
||||||
<g clip-path="url(#clip3)" clip-rule="nonzero">
|
<g clip-path="url(#clip3)" clip-rule="nonzero">
|
||||||
<g style="fill:rgb(0%,0%,0%);fill-opacity:1;">
|
<g style="fill:rgb(0%,0%,0%);fill-opacity:1;">
|
||||||
<use xlink:href="#glyph0-18" x="1068.0625" y="58"/>
|
<use xlink:href="#glyph0-18" x="945.597656" y="90"/>
|
||||||
<use xlink:href="#glyph0-7" x="1072.767578" y="58"/>
|
<use xlink:href="#glyph0-7" x="950.302734" y="90"/>
|
||||||
<use xlink:href="#glyph0-2" x="1077.701172" y="58"/>
|
<use xlink:href="#glyph0-2" x="955.236328" y="90"/>
|
||||||
<use xlink:href="#glyph0-3" x="1085.054688" y="58"/>
|
<use xlink:href="#glyph0-3" x="962.589844" y="90"/>
|
||||||
<use xlink:href="#glyph0-19" x="1091.652344" y="58"/>
|
<use xlink:href="#glyph0-19" x="969.1875" y="90"/>
|
||||||
<use xlink:href="#glyph0-20" x="1099.035156" y="58"/>
|
<use xlink:href="#glyph0-20" x="976.570312" y="90"/>
|
||||||
<use xlink:href="#glyph0-13" x="1102.369141" y="58"/>
|
<use xlink:href="#glyph0-13" x="979.904297" y="90"/>
|
||||||
</g>
|
</g>
|
||||||
</g>
|
</g>
|
||||||
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,80%,40%);fill-opacity:1;" d="M 1099.445312 46 L 1190.574219 46 L 1190.574219 60 L 1099.445312 60 Z M 1099.445312 46 "/>
|
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,80%,40%);fill-opacity:1;" d="M 996.683594 78 L 1006.457031 78 L 1006.457031 92 L 996.683594 92 Z M 996.683594 78 "/>
|
||||||
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,80%,40%);fill-opacity:1;" d="M 93.207031 78 L 97.839844 78 L 97.839844 92 L 93.207031 92 Z M 93.207031 78 "/>
|
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,40%,40%);fill-opacity:1;" d="M 1006.460938 78 L 1003.683594 78 L 1003.683594 92 L 1006.460938 92 Z M 1006.460938 78 "/>
|
||||||
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,80%,40%);fill-opacity:1;" d="M 97.839844 78 L 311.714844 78 L 311.714844 92 L 97.839844 92 Z M 97.839844 78 "/>
|
<path style="fill:none;stroke-width:1;stroke-linecap:butt;stroke-linejoin:miter;stroke:rgb(0%,0%,0%);stroke-opacity:1;stroke-miterlimit:10;" d="M 248.011719 81 L 248.011719 75 "/>
|
||||||
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(50%,90%,50%);fill-opacity:1;" d="M 311.714844 78 L 657.222656 78 L 657.222656 92 L 311.714844 92 Z M 311.714844 78 "/>
|
|
||||||
<g style="fill:rgb(0%,0%,0%);fill-opacity:1;">
|
|
||||||
<use xlink:href="#glyph0-18" x="313.714844" y="90"/>
|
|
||||||
<use xlink:href="#glyph0-7" x="318.419922" y="90"/>
|
|
||||||
<use xlink:href="#glyph0-2" x="323.353516" y="90"/>
|
|
||||||
<use xlink:href="#glyph0-3" x="330.707031" y="90"/>
|
|
||||||
<use xlink:href="#glyph0-19" x="337.304688" y="90"/>
|
|
||||||
<use xlink:href="#glyph0-20" x="344.6875" y="90"/>
|
|
||||||
<use xlink:href="#glyph0-13" x="348.021484" y="90"/>
|
|
||||||
</g>
|
|
||||||
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,80%,40%);fill-opacity:1;" d="M 657.222656 78 L 662.550781 78 L 662.550781 92 L 657.222656 92 Z M 657.222656 78 "/>
|
|
||||||
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,40%,40%);fill-opacity:1;" d="M 662.550781 78 L 856.289062 78 L 856.289062 92 L 662.550781 92 Z M 662.550781 78 "/>
|
|
||||||
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,80%,40%);fill-opacity:1;" d="M 856.289062 78 L 863.34375 78 L 863.34375 92 L 856.289062 92 Z M 856.289062 78 "/>
|
|
||||||
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(50%,90%,50%);fill-opacity:1;" d="M 863.34375 78 L 898 78 L 898 92 L 863.34375 92 Z M 863.34375 78 "/>
|
|
||||||
<g clip-path="url(#clip4)" clip-rule="nonzero">
|
<g clip-path="url(#clip4)" clip-rule="nonzero">
|
||||||
<g style="fill:rgb(0%,0%,0%);fill-opacity:1;">
|
<g style="fill:rgb(0%,0%,0%);fill-opacity:1;">
|
||||||
<use xlink:href="#glyph0-18" x="865.34375" y="90"/>
|
<use xlink:href="#glyph1-1" x="250.011719" y="76"/>
|
||||||
<use xlink:href="#glyph0-7" x="870.048828" y="90"/>
|
<use xlink:href="#glyph1-2" x="252.371094" y="76"/>
|
||||||
<use xlink:href="#glyph0-2" x="874.982422" y="90"/>
|
<use xlink:href="#glyph1-3" x="257.265625" y="76"/>
|
||||||
<use xlink:href="#glyph0-3" x="882.335938" y="90"/>
|
<use xlink:href="#glyph1-4" x="262.34375" y="76"/>
|
||||||
<use xlink:href="#glyph0-19" x="888.933594" y="90"/>
|
<use xlink:href="#glyph1-5" x="264.886719" y="76"/>
|
||||||
<use xlink:href="#glyph0-20" x="896.316406" y="90"/>
|
<use xlink:href="#glyph1-4" x="269.976562" y="76"/>
|
||||||
<use xlink:href="#glyph0-13" x="899.650391" y="90"/>
|
<use xlink:href="#glyph1-6" x="272.519531" y="76"/>
|
||||||
|
<use xlink:href="#glyph1-7" x="276.6875" y="76"/>
|
||||||
|
<use xlink:href="#glyph1-8" x="279.824219" y="76"/>
|
||||||
|
<use xlink:href="#glyph1-9" x="284.726562" y="76"/>
|
||||||
|
<use xlink:href="#glyph1-7" x="288.015625" y="76"/>
|
||||||
|
<use xlink:href="#glyph1-10" x="291.152344" y="76"/>
|
||||||
|
<use xlink:href="#glyph1-11" x="293.375" y="76"/>
|
||||||
|
<use xlink:href="#glyph1-12" x="298.445312" y="76"/>
|
||||||
</g>
|
</g>
|
||||||
</g>
|
</g>
|
||||||
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,80%,40%);fill-opacity:1;" d="M 898 78 L 899.648438 78 L 899.648438 92 L 898 92 Z M 898 78 "/>
|
<path style="fill:none;stroke-width:1;stroke-linecap:butt;stroke-linejoin:miter;stroke:rgb(0%,0%,0%);stroke-opacity:1;stroke-miterlimit:10;" d="M 977.003906 81 L 977.003906 75 "/>
|
||||||
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,40%,40%);fill-opacity:1;" d="M 899.652344 78 L 943.257812 78 L 943.257812 92 L 899.652344 92 Z M 899.652344 78 "/>
|
|
||||||
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,80%,40%);fill-opacity:1;" d="M 943.257812 78 L 949.027344 78 L 949.027344 92 L 943.257812 92 Z M 943.257812 78 "/>
|
|
||||||
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(50%,90%,50%);fill-opacity:1;" d="M 949.027344 78 L 981.15625 78 L 981.15625 92 L 949.027344 92 Z M 949.027344 78 "/>
|
|
||||||
<g clip-path="url(#clip5)" clip-rule="nonzero">
|
<g clip-path="url(#clip5)" clip-rule="nonzero">
|
||||||
<g style="fill:rgb(0%,0%,0%);fill-opacity:1;">
|
<g style="fill:rgb(0%,0%,0%);fill-opacity:1;">
|
||||||
<use xlink:href="#glyph0-18" x="951.027344" y="90"/>
|
<use xlink:href="#glyph1-5" x="979.003906" y="76"/>
|
||||||
<use xlink:href="#glyph0-7" x="955.732422" y="90"/>
|
<use xlink:href="#glyph1-4" x="984.09375" y="76"/>
|
||||||
<use xlink:href="#glyph0-2" x="960.666016" y="90"/>
|
<use xlink:href="#glyph1-13" x="986.636719" y="76"/>
|
||||||
<use xlink:href="#glyph0-3" x="968.019531" y="90"/>
|
<use xlink:href="#glyph1-2" x="991.714844" y="76"/>
|
||||||
<use xlink:href="#glyph0-19" x="974.617188" y="90"/>
|
<use xlink:href="#glyph1-11" x="996.609375" y="76"/>
|
||||||
<use xlink:href="#glyph0-20" x="982" y="90"/>
|
<use xlink:href="#glyph1-14" x="1001.679688" y="76"/>
|
||||||
<use xlink:href="#glyph0-13" x="985.333984" y="90"/>
|
|
||||||
</g>
|
</g>
|
||||||
</g>
|
</g>
|
||||||
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,80%,40%);fill-opacity:1;" d="M 981.152344 78 L 982.46875 78 L 982.46875 92 L 981.152344 92 Z M 981.152344 78 "/>
|
<path style="fill:none;stroke-width:1;stroke-linecap:butt;stroke-linejoin:miter;stroke:rgb(40%,80%,40%);stroke-opacity:1;stroke-miterlimit:10;" d="M 59.886719 46 L 59.886719 92 "/>
|
||||||
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,40%,40%);fill-opacity:1;" d="M 982.472656 78 L 1041.113281 78 L 1041.113281 92 L 982.472656 92 Z M 982.472656 78 "/>
|
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,80%,40%);fill-opacity:1;" d="M 523.035156 110 L 525.679688 110 L 525.679688 124 L 523.035156 124 Z M 523.035156 110 "/>
|
||||||
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,80%,40%);fill-opacity:1;" d="M 1041.109375 78 L 1048.574219 78 L 1048.574219 92 L 1041.109375 92 Z M 1041.109375 78 "/>
|
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,80%,40%);fill-opacity:1;" d="M 525.679688 110 L 544.980469 110 L 544.980469 124 L 525.679688 124 Z M 525.679688 110 "/>
|
||||||
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,40%,40%);fill-opacity:1;" d="M 1048.574219 78 L 1046.953125 78 L 1046.953125 92 L 1048.574219 92 Z M 1048.574219 78 "/>
|
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(50%,90%,50%);fill-opacity:1;" d="M 544.976562 110 L 611.632812 110 L 611.632812 124 L 544.976562 124 Z M 544.976562 110 "/>
|
||||||
<path style="fill:none;stroke-width:1;stroke-linecap:butt;stroke-linejoin:miter;stroke:rgb(0%,0%,0%);stroke-opacity:1;stroke-miterlimit:10;" d="M 430.597656 81 L 430.597656 75 "/>
|
|
||||||
<g style="fill:rgb(0%,0%,0%);fill-opacity:1;">
|
<g style="fill:rgb(0%,0%,0%);fill-opacity:1;">
|
||||||
<use xlink:href="#glyph1-1" x="432.597656" y="76"/>
|
<use xlink:href="#glyph0-18" x="546.976562" y="122"/>
|
||||||
<use xlink:href="#glyph1-2" x="434.820312" y="76"/>
|
<use xlink:href="#glyph0-7" x="551.681641" y="122"/>
|
||||||
<use xlink:href="#glyph1-3" x="437.363281" y="76"/>
|
<use xlink:href="#glyph0-2" x="556.615234" y="122"/>
|
||||||
<use xlink:href="#glyph1-2" x="444.066406" y="76"/>
|
<use xlink:href="#glyph0-3" x="563.96875" y="122"/>
|
||||||
<use xlink:href="#glyph1-4" x="446.609375" y="76"/>
|
<use xlink:href="#glyph0-19" x="570.566406" y="122"/>
|
||||||
|
<use xlink:href="#glyph0-20" x="577.949219" y="122"/>
|
||||||
|
<use xlink:href="#glyph0-13" x="581.283203" y="122"/>
|
||||||
</g>
|
</g>
|
||||||
<path style="fill:none;stroke-width:1;stroke-linecap:butt;stroke-linejoin:miter;stroke:rgb(0%,0%,0%);stroke-opacity:1;stroke-miterlimit:10;" d="M 886.390625 81 L 886.390625 75 "/>
|
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,80%,40%);fill-opacity:1;" d="M 611.636719 110 L 615.625 110 L 615.625 124 L 611.636719 124 Z M 611.636719 110 "/>
|
||||||
<g style="fill:rgb(0%,0%,0%);fill-opacity:1;">
|
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,40%,40%);fill-opacity:1;" d="M 615.621094 110 L 1006.457031 110 L 1006.457031 124 L 615.621094 124 Z M 615.621094 110 "/>
|
||||||
<use xlink:href="#glyph1-1" x="888.390625" y="76"/>
|
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,80%,40%);fill-opacity:1;" d="M 1006.460938 110 L 1016.121094 110 L 1016.121094 124 L 1006.460938 124 Z M 1006.460938 110 "/>
|
||||||
<use xlink:href="#glyph1-2" x="890.613281" y="76"/>
|
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(50%,90%,50%);fill-opacity:1;" d="M 1016.117188 110 L 1065.160156 110 L 1065.160156 124 L 1016.117188 124 Z M 1016.117188 110 "/>
|
||||||
<use xlink:href="#glyph1-3" x="893.15625" y="76"/>
|
|
||||||
<use xlink:href="#glyph1-2" x="899.859375" y="76"/>
|
|
||||||
<use xlink:href="#glyph1-5" x="902.402344" y="76"/>
|
|
||||||
</g>
|
|
||||||
<path style="fill:none;stroke-width:1;stroke-linecap:butt;stroke-linejoin:miter;stroke:rgb(0%,0%,0%);stroke-opacity:1;stroke-miterlimit:10;" d="M 970.753906 81 L 970.753906 75 "/>
|
|
||||||
<g style="fill:rgb(0%,0%,0%);fill-opacity:1;">
|
|
||||||
<use xlink:href="#glyph1-1" x="972.753906" y="76"/>
|
|
||||||
<use xlink:href="#glyph1-2" x="974.976562" y="76"/>
|
|
||||||
<use xlink:href="#glyph1-3" x="977.519531" y="76"/>
|
|
||||||
<use xlink:href="#glyph1-2" x="984.222656" y="76"/>
|
|
||||||
<use xlink:href="#glyph1-6" x="986.765625" y="76"/>
|
|
||||||
</g>
|
|
||||||
<path style="fill:none;stroke-width:1;stroke-linecap:butt;stroke-linejoin:miter;stroke:rgb(40%,80%,40%);stroke-opacity:1;stroke-miterlimit:10;" d="M 93.207031 46 L 93.207031 92 "/>
|
|
||||||
<path style="fill:none;stroke-width:1;stroke-linecap:butt;stroke-linejoin:miter;stroke:rgb(0%,0%,0%);stroke-opacity:1;stroke-miterlimit:10;" d="M 713.289062 49 L 713.289062 43 "/>
|
|
||||||
<g style="fill:rgb(0%,0%,0%);fill-opacity:1;">
|
|
||||||
<use xlink:href="#glyph1-7" x="715.289062" y="44"/>
|
|
||||||
<use xlink:href="#glyph1-1" x="719.890625" y="44"/>
|
|
||||||
<use xlink:href="#glyph1-8" x="722.113281" y="44"/>
|
|
||||||
<use xlink:href="#glyph1-9" x="725.402344" y="44"/>
|
|
||||||
<use xlink:href="#glyph1-10" x="729.570312" y="44"/>
|
|
||||||
<use xlink:href="#glyph1-2" x="732.707031" y="44"/>
|
|
||||||
<use xlink:href="#glyph1-10" x="735.25" y="44"/>
|
|
||||||
<use xlink:href="#glyph1-11" x="738.386719" y="44"/>
|
|
||||||
<use xlink:href="#glyph1-8" x="743.457031" y="44"/>
|
|
||||||
<use xlink:href="#glyph1-12" x="746.746094" y="44"/>
|
|
||||||
<use xlink:href="#glyph1-13" x="751.667969" y="44"/>
|
|
||||||
<use xlink:href="#glyph1-14" x="756.570312" y="44"/>
|
|
||||||
<use xlink:href="#glyph1-2" x="761.648438" y="44"/>
|
|
||||||
<use xlink:href="#glyph1-15" x="764.191406" y="44"/>
|
|
||||||
<use xlink:href="#glyph1-16" x="767.007812" y="44"/>
|
|
||||||
<use xlink:href="#glyph1-8" x="771.902344" y="44"/>
|
|
||||||
<use xlink:href="#glyph1-17" x="775.191406" y="44"/>
|
|
||||||
<use xlink:href="#glyph1-12" x="779.824219" y="44"/>
|
|
||||||
<use xlink:href="#glyph1-14" x="784.746094" y="44"/>
|
|
||||||
</g>
|
|
||||||
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,80%,40%);fill-opacity:1;" d="M 740.554688 110 L 742.976562 110 L 742.976562 124 L 740.554688 124 Z M 740.554688 110 "/>
|
|
||||||
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,80%,40%);fill-opacity:1;" d="M 742.976562 110 L 762.324219 110 L 762.324219 124 L 742.976562 124 Z M 742.976562 110 "/>
|
|
||||||
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(50%,90%,50%);fill-opacity:1;" d="M 762.328125 110 L 801.253906 110 L 801.253906 124 L 762.328125 124 Z M 762.328125 110 "/>
|
|
||||||
<g clip-path="url(#clip6)" clip-rule="nonzero">
|
<g clip-path="url(#clip6)" clip-rule="nonzero">
|
||||||
<g style="fill:rgb(0%,0%,0%);fill-opacity:1;">
|
<g style="fill:rgb(0%,0%,0%);fill-opacity:1;">
|
||||||
<use xlink:href="#glyph0-18" x="764.328125" y="122"/>
|
<use xlink:href="#glyph0-18" x="1018.117188" y="122"/>
|
||||||
<use xlink:href="#glyph0-7" x="769.033203" y="122"/>
|
<use xlink:href="#glyph0-7" x="1022.822266" y="122"/>
|
||||||
<use xlink:href="#glyph0-2" x="773.966797" y="122"/>
|
<use xlink:href="#glyph0-2" x="1027.755859" y="122"/>
|
||||||
<use xlink:href="#glyph0-3" x="781.320312" y="122"/>
|
<use xlink:href="#glyph0-3" x="1035.109375" y="122"/>
|
||||||
<use xlink:href="#glyph0-19" x="787.917969" y="122"/>
|
<use xlink:href="#glyph0-19" x="1041.707031" y="122"/>
|
||||||
<use xlink:href="#glyph0-20" x="795.300781" y="122"/>
|
<use xlink:href="#glyph0-20" x="1049.089844" y="122"/>
|
||||||
<use xlink:href="#glyph0-13" x="798.634766" y="122"/>
|
<use xlink:href="#glyph0-13" x="1052.423828" y="122"/>
|
||||||
</g>
|
</g>
|
||||||
</g>
|
</g>
|
||||||
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,80%,40%);fill-opacity:1;" d="M 801.253906 110 L 803.496094 110 L 803.496094 124 L 801.253906 124 Z M 801.253906 110 "/>
|
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,80%,40%);fill-opacity:1;" d="M 1065.164062 110 L 1071.8125 110 L 1071.8125 124 L 1065.164062 124 Z M 1065.164062 110 "/>
|
||||||
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,40%,40%);fill-opacity:1;" d="M 803.496094 110 L 901.589844 110 L 901.589844 124 L 803.496094 124 Z M 803.496094 110 "/>
|
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,40%,40%);fill-opacity:1;" d="M 1071.8125 110 L 1070.394531 110 L 1070.394531 124 L 1071.8125 124 Z M 1071.8125 110 "/>
|
||||||
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,80%,40%);fill-opacity:1;" d="M 901.589844 110 L 907.84375 110 L 907.84375 124 L 901.589844 124 Z M 901.589844 110 "/>
|
<path style="fill:none;stroke-width:1;stroke-linecap:butt;stroke-linejoin:miter;stroke:rgb(0%,0%,0%);stroke-opacity:1;stroke-miterlimit:10;" d="M 581.375 113 L 581.375 107 "/>
|
||||||
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(50%,90%,50%);fill-opacity:1;" d="M 907.84375 110 L 939.957031 110 L 939.957031 124 L 907.84375 124 Z M 907.84375 110 "/>
|
|
||||||
<g clip-path="url(#clip7)" clip-rule="nonzero">
|
<g clip-path="url(#clip7)" clip-rule="nonzero">
|
||||||
<g style="fill:rgb(0%,0%,0%);fill-opacity:1;">
|
<g style="fill:rgb(0%,0%,0%);fill-opacity:1;">
|
||||||
<use xlink:href="#glyph0-18" x="909.84375" y="122"/>
|
<use xlink:href="#glyph1-1" x="583.375" y="108"/>
|
||||||
<use xlink:href="#glyph0-7" x="914.548828" y="122"/>
|
<use xlink:href="#glyph1-2" x="585.734375" y="108"/>
|
||||||
<use xlink:href="#glyph0-2" x="919.482422" y="122"/>
|
<use xlink:href="#glyph1-3" x="590.628906" y="108"/>
|
||||||
<use xlink:href="#glyph0-3" x="926.835938" y="122"/>
|
<use xlink:href="#glyph1-4" x="595.707031" y="108"/>
|
||||||
<use xlink:href="#glyph0-19" x="933.433594" y="122"/>
|
<use xlink:href="#glyph1-15" x="598.25" y="108"/>
|
||||||
<use xlink:href="#glyph0-20" x="940.816406" y="122"/>
|
<use xlink:href="#glyph1-4" x="603.339844" y="108"/>
|
||||||
<use xlink:href="#glyph0-13" x="944.150391" y="122"/>
|
<use xlink:href="#glyph1-6" x="605.882812" y="108"/>
|
||||||
|
<use xlink:href="#glyph1-7" x="610.050781" y="108"/>
|
||||||
|
<use xlink:href="#glyph1-8" x="613.1875" y="108"/>
|
||||||
|
<use xlink:href="#glyph1-9" x="618.089844" y="108"/>
|
||||||
|
<use xlink:href="#glyph1-7" x="621.378906" y="108"/>
|
||||||
|
<use xlink:href="#glyph1-10" x="624.515625" y="108"/>
|
||||||
|
<use xlink:href="#glyph1-11" x="626.738281" y="108"/>
|
||||||
|
<use xlink:href="#glyph1-12" x="631.808594" y="108"/>
|
||||||
</g>
|
</g>
|
||||||
</g>
|
</g>
|
||||||
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,80%,40%);fill-opacity:1;" d="M 939.957031 110 L 941.289062 110 L 941.289062 124 L 939.957031 124 Z M 939.957031 110 "/>
|
<path style="fill:none;stroke-width:1;stroke-linecap:butt;stroke-linejoin:miter;stroke:rgb(0%,0%,0%);stroke-opacity:1;stroke-miterlimit:10;" d="M 1047.300781 113 L 1047.300781 107 "/>
|
||||||
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,40%,40%);fill-opacity:1;" d="M 941.289062 110 L 984.167969 110 L 984.167969 124 L 941.289062 124 Z M 941.289062 110 "/>
|
|
||||||
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,80%,40%);fill-opacity:1;" d="M 984.167969 110 L 1005.09375 110 L 1005.09375 124 L 984.167969 124 Z M 984.167969 110 "/>
|
|
||||||
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(50%,90%,50%);fill-opacity:1;" d="M 1005.089844 110 L 1022.230469 110 L 1022.230469 124 L 1005.089844 124 Z M 1005.089844 110 "/>
|
|
||||||
<g clip-path="url(#clip8)" clip-rule="nonzero">
|
<g clip-path="url(#clip8)" clip-rule="nonzero">
|
||||||
<g style="fill:rgb(0%,0%,0%);fill-opacity:1;">
|
<g style="fill:rgb(0%,0%,0%);fill-opacity:1;">
|
||||||
<use xlink:href="#glyph0-18" x="1007.089844" y="122"/>
|
<use xlink:href="#glyph1-15" x="1049.300781" y="108"/>
|
||||||
<use xlink:href="#glyph0-7" x="1011.794922" y="122"/>
|
<use xlink:href="#glyph1-4" x="1054.390625" y="108"/>
|
||||||
<use xlink:href="#glyph0-2" x="1016.728516" y="122"/>
|
<use xlink:href="#glyph1-13" x="1056.933594" y="108"/>
|
||||||
<use xlink:href="#glyph0-3" x="1024.082031" y="122"/>
|
<use xlink:href="#glyph1-2" x="1062.011719" y="108"/>
|
||||||
<use xlink:href="#glyph0-19" x="1030.679688" y="122"/>
|
<use xlink:href="#glyph1-11" x="1066.90625" y="108"/>
|
||||||
<use xlink:href="#glyph0-20" x="1038.0625" y="122"/>
|
<use xlink:href="#glyph1-14" x="1071.976562" y="108"/>
|
||||||
<use xlink:href="#glyph0-13" x="1041.396484" y="122"/>
|
|
||||||
</g>
|
</g>
|
||||||
</g>
|
</g>
|
||||||
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,80%,40%);fill-opacity:1;" d="M 1022.230469 110 L 1023.820312 110 L 1023.820312 124 L 1022.230469 124 Z M 1022.230469 110 "/>
|
<path style="fill:none;stroke-width:1;stroke-linecap:butt;stroke-linejoin:miter;stroke:rgb(40%,80%,40%);stroke-opacity:1;stroke-miterlimit:10;" d="M 523.035156 46 L 523.035156 124 "/>
|
||||||
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,40%,40%);fill-opacity:1;" d="M 1023.820312 110 L 1048.574219 110 L 1048.574219 124 L 1023.820312 124 Z M 1023.820312 110 "/>
|
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,80%,40%);fill-opacity:1;" d="M 621.21875 142 L 622.960938 142 L 622.960938 156 L 621.21875 156 Z M 621.21875 142 "/>
|
||||||
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,80%,40%);fill-opacity:1;" d="M 1048.574219 110 L 1053.917969 110 L 1053.917969 124 L 1048.574219 124 Z M 1048.574219 110 "/>
|
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,80%,40%);fill-opacity:1;" d="M 622.960938 142 L 634.785156 142 L 634.785156 156 L 622.960938 156 Z M 622.960938 142 "/>
|
||||||
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,40%,40%);fill-opacity:1;" d="M 1053.917969 110 L 1052.722656 110 L 1052.722656 124 L 1053.917969 124 Z M 1053.917969 110 "/>
|
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(50%,90%,50%);fill-opacity:1;" d="M 634.785156 142 L 838.511719 142 L 838.511719 156 L 634.785156 156 Z M 634.785156 142 "/>
|
||||||
<path style="fill:none;stroke-width:1;stroke-linecap:butt;stroke-linejoin:miter;stroke:rgb(0%,0%,0%);stroke-opacity:1;stroke-miterlimit:10;" d="M 787.792969 113 L 787.792969 107 "/>
|
<g style="fill:rgb(0%,0%,0%);fill-opacity:1;">
|
||||||
|
<use xlink:href="#glyph0-18" x="636.785156" y="154"/>
|
||||||
|
<use xlink:href="#glyph0-7" x="641.490234" y="154"/>
|
||||||
|
<use xlink:href="#glyph0-2" x="646.423828" y="154"/>
|
||||||
|
<use xlink:href="#glyph0-3" x="653.777344" y="154"/>
|
||||||
|
<use xlink:href="#glyph0-19" x="660.375" y="154"/>
|
||||||
|
<use xlink:href="#glyph0-20" x="667.757812" y="154"/>
|
||||||
|
<use xlink:href="#glyph0-13" x="671.091797" y="154"/>
|
||||||
|
</g>
|
||||||
|
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,80%,40%);fill-opacity:1;" d="M 838.515625 142 L 861.878906 142 L 861.878906 156 L 838.515625 156 Z M 838.515625 142 "/>
|
||||||
|
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,40%,40%);fill-opacity:1;" d="M 861.875 142 L 1071.8125 142 L 1071.8125 156 L 861.875 156 Z M 861.875 142 "/>
|
||||||
|
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,80%,40%);fill-opacity:1;" d="M 1071.8125 142 L 1080.300781 142 L 1080.300781 156 L 1071.8125 156 Z M 1071.8125 142 "/>
|
||||||
|
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(50%,90%,50%);fill-opacity:1;" d="M 1080.304688 142 L 1126.570312 142 L 1126.570312 156 L 1080.304688 156 Z M 1080.304688 142 "/>
|
||||||
<g clip-path="url(#clip9)" clip-rule="nonzero">
|
<g clip-path="url(#clip9)" clip-rule="nonzero">
|
||||||
<g style="fill:rgb(0%,0%,0%);fill-opacity:1;">
|
<g style="fill:rgb(0%,0%,0%);fill-opacity:1;">
|
||||||
<use xlink:href="#glyph1-18" x="789.792969" y="108"/>
|
<use xlink:href="#glyph0-18" x="1082.304688" y="154"/>
|
||||||
<use xlink:href="#glyph1-2" x="792.015625" y="108"/>
|
<use xlink:href="#glyph0-7" x="1087.009766" y="154"/>
|
||||||
<use xlink:href="#glyph1-3" x="794.558594" y="108"/>
|
<use xlink:href="#glyph0-2" x="1091.943359" y="154"/>
|
||||||
<use xlink:href="#glyph1-2" x="801.261719" y="108"/>
|
<use xlink:href="#glyph0-3" x="1099.296875" y="154"/>
|
||||||
<use xlink:href="#glyph1-4" x="803.804688" y="108"/>
|
<use xlink:href="#glyph0-19" x="1105.894531" y="154"/>
|
||||||
|
<use xlink:href="#glyph0-20" x="1113.277344" y="154"/>
|
||||||
|
<use xlink:href="#glyph0-13" x="1116.611328" y="154"/>
|
||||||
</g>
|
</g>
|
||||||
</g>
|
</g>
|
||||||
<path style="fill:none;stroke-width:1;stroke-linecap:butt;stroke-linejoin:miter;stroke:rgb(0%,0%,0%);stroke-opacity:1;stroke-miterlimit:10;" d="M 929.160156 113 L 929.160156 107 "/>
|
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,80%,40%);fill-opacity:1;" d="M 1126.566406 142 L 1134.214844 142 L 1134.214844 156 L 1126.566406 156 Z M 1126.566406 142 "/>
|
||||||
|
<path style=" stroke:none;fill-rule:nonzero;fill:rgb(40%,40%,40%);fill-opacity:1;" d="M 1134.214844 142 L 1132.316406 142 L 1132.316406 156 L 1134.214844 156 Z M 1134.214844 142 "/>
|
||||||
|
<path style="fill:none;stroke-width:1;stroke-linecap:butt;stroke-linejoin:miter;stroke:rgb(0%,0%,0%);stroke-opacity:1;stroke-miterlimit:10;" d="M 817.433594 145 L 817.433594 139 "/>
|
||||||
<g clip-path="url(#clip10)" clip-rule="nonzero">
|
<g clip-path="url(#clip10)" clip-rule="nonzero">
|
||||||
<g style="fill:rgb(0%,0%,0%);fill-opacity:1;">
|
<g style="fill:rgb(0%,0%,0%);fill-opacity:1;">
|
||||||
<use xlink:href="#glyph1-18" x="931.160156" y="108"/>
|
<use xlink:href="#glyph1-1" x="819.433594" y="140"/>
|
||||||
<use xlink:href="#glyph1-2" x="933.382812" y="108"/>
|
<use xlink:href="#glyph1-2" x="821.792969" y="140"/>
|
||||||
<use xlink:href="#glyph1-3" x="935.925781" y="108"/>
|
<use xlink:href="#glyph1-3" x="826.6875" y="140"/>
|
||||||
<use xlink:href="#glyph1-2" x="942.628906" y="108"/>
|
<use xlink:href="#glyph1-4" x="831.765625" y="140"/>
|
||||||
<use xlink:href="#glyph1-5" x="945.171875" y="108"/>
|
<use xlink:href="#glyph1-16" x="834.308594" y="140"/>
|
||||||
|
<use xlink:href="#glyph1-4" x="839.398438" y="140"/>
|
||||||
|
<use xlink:href="#glyph1-6" x="841.941406" y="140"/>
|
||||||
|
<use xlink:href="#glyph1-7" x="846.109375" y="140"/>
|
||||||
|
<use xlink:href="#glyph1-8" x="849.246094" y="140"/>
|
||||||
|
<use xlink:href="#glyph1-9" x="854.148438" y="140"/>
|
||||||
|
<use xlink:href="#glyph1-7" x="857.4375" y="140"/>
|
||||||
|
<use xlink:href="#glyph1-10" x="860.574219" y="140"/>
|
||||||
|
<use xlink:href="#glyph1-11" x="862.796875" y="140"/>
|
||||||
|
<use xlink:href="#glyph1-12" x="867.867188" y="140"/>
|
||||||
</g>
|
</g>
|
||||||
</g>
|
</g>
|
||||||
<path style="fill:none;stroke-width:1;stroke-linecap:butt;stroke-linejoin:miter;stroke:rgb(0%,0%,0%);stroke-opacity:1;stroke-miterlimit:10;" d="M 1011.980469 113 L 1011.980469 107 "/>
|
<path style="fill:none;stroke-width:1;stroke-linecap:butt;stroke-linejoin:miter;stroke:rgb(0%,0%,0%);stroke-opacity:1;stroke-miterlimit:10;" d="M 1109.605469 145 L 1109.605469 139 "/>
|
||||||
<g clip-path="url(#clip11)" clip-rule="nonzero">
|
<g clip-path="url(#clip11)" clip-rule="nonzero">
|
||||||
<g style="fill:rgb(0%,0%,0%);fill-opacity:1;">
|
<g style="fill:rgb(0%,0%,0%);fill-opacity:1;">
|
||||||
<use xlink:href="#glyph1-18" x="1013.980469" y="108"/>
|
<use xlink:href="#glyph1-16" x="1111.605469" y="140"/>
|
||||||
<use xlink:href="#glyph1-2" x="1016.203125" y="108"/>
|
<use xlink:href="#glyph1-4" x="1116.695312" y="140"/>
|
||||||
<use xlink:href="#glyph1-3" x="1018.746094" y="108"/>
|
<use xlink:href="#glyph1-13" x="1119.238281" y="140"/>
|
||||||
<use xlink:href="#glyph1-2" x="1025.449219" y="108"/>
|
<use xlink:href="#glyph1-2" x="1124.316406" y="140"/>
|
||||||
<use xlink:href="#glyph1-6" x="1027.992188" y="108"/>
|
<use xlink:href="#glyph1-11" x="1129.210938" y="140"/>
|
||||||
|
<use xlink:href="#glyph1-14" x="1134.28125" y="140"/>
|
||||||
</g>
|
</g>
|
||||||
</g>
|
</g>
|
||||||
<path style="fill:none;stroke-width:1;stroke-linecap:butt;stroke-linejoin:miter;stroke:rgb(40%,80%,40%);stroke-opacity:1;stroke-miterlimit:10;" d="M 740.554688 46 L 740.554688 124 "/>
|
<path style="fill:none;stroke-width:1;stroke-linecap:butt;stroke-linejoin:miter;stroke:rgb(40%,80%,40%);stroke-opacity:1;stroke-miterlimit:10;" d="M 621.21875 46 L 621.21875 156 "/>
|
||||||
<path style="fill:none;stroke-width:1;stroke-linecap:butt;stroke-linejoin:miter;stroke:rgb(0%,0%,0%);stroke-opacity:1;stroke-miterlimit:10;" d="M 834.167969 49 L 834.167969 43 "/>
|
<path style="fill:none;stroke-width:1;stroke-linecap:butt;stroke-linejoin:miter;stroke:rgb(0%,0%,0%);stroke-opacity:1;stroke-miterlimit:10;" d="M 899.039062 49 L 899.039062 43 "/>
|
||||||
<g clip-path="url(#clip12)" clip-rule="nonzero">
|
<g clip-path="url(#clip12)" clip-rule="nonzero">
|
||||||
<g style="fill:rgb(0%,0%,0%);fill-opacity:1;">
|
<g style="fill:rgb(0%,0%,0%);fill-opacity:1;">
|
||||||
<use xlink:href="#glyph1-19" x="836.167969" y="44"/>
|
<use xlink:href="#glyph1-17" x="901.039062" y="44"/>
|
||||||
<use xlink:href="#glyph1-12" x="841.246094" y="44"/>
|
<use xlink:href="#glyph1-18" x="906.511719" y="44"/>
|
||||||
<use xlink:href="#glyph1-20" x="846.167969" y="44"/>
|
<use xlink:href="#glyph1-18" x="908.734375" y="44"/>
|
||||||
<use xlink:href="#glyph1-16" x="850.566406" y="44"/>
|
<use xlink:href="#glyph1-4" x="910.957031" y="44"/>
|
||||||
<use xlink:href="#glyph1-21" x="855.460938" y="44"/>
|
<use xlink:href="#glyph1-19" x="913.5" y="44"/>
|
||||||
<use xlink:href="#glyph1-14" x="860.53125" y="44"/>
|
<use xlink:href="#glyph1-20" x="917.898438" y="44"/>
|
||||||
<use xlink:href="#glyph1-2" x="865.609375" y="44"/>
|
<use xlink:href="#glyph1-10" x="922.96875" y="44"/>
|
||||||
<use xlink:href="#glyph1-10" x="868.152344" y="44"/>
|
<use xlink:href="#glyph1-18" x="925.191406" y="44"/>
|
||||||
<use xlink:href="#glyph1-11" x="871.289062" y="44"/>
|
<use xlink:href="#glyph1-13" x="927.414062" y="44"/>
|
||||||
<use xlink:href="#glyph1-8" x="876.359375" y="44"/>
|
<use xlink:href="#glyph1-4" x="932.492188" y="44"/>
|
||||||
<use xlink:href="#glyph1-12" x="879.648438" y="44"/>
|
<use xlink:href="#glyph1-21" x="935.035156" y="44"/>
|
||||||
<use xlink:href="#glyph1-13" x="884.570312" y="44"/>
|
<use xlink:href="#glyph1-10" x="937.851562" y="44"/>
|
||||||
<use xlink:href="#glyph1-14" x="889.472656" y="44"/>
|
<use xlink:href="#glyph1-3" x="940.074219" y="44"/>
|
||||||
<use xlink:href="#glyph1-2" x="894.550781" y="44"/>
|
<use xlink:href="#glyph1-14" x="945.152344" y="44"/>
|
||||||
<use xlink:href="#glyph1-15" x="897.09375" y="44"/>
|
<use xlink:href="#glyph1-9" x="950.074219" y="44"/>
|
||||||
<use xlink:href="#glyph1-16" x="899.910156" y="44"/>
|
<use xlink:href="#glyph1-6" x="953.363281" y="44"/>
|
||||||
<use xlink:href="#glyph1-8" x="904.804688" y="44"/>
|
<use xlink:href="#glyph1-4" x="957.53125" y="44"/>
|
||||||
<use xlink:href="#glyph1-17" x="908.09375" y="44"/>
|
<use xlink:href="#glyph1-21" x="960.074219" y="44"/>
|
||||||
<use xlink:href="#glyph1-12" x="912.726562" y="44"/>
|
<use xlink:href="#glyph1-2" x="962.890625" y="44"/>
|
||||||
<use xlink:href="#glyph1-14" x="917.648438" y="44"/>
|
<use xlink:href="#glyph1-9" x="967.785156" y="44"/>
|
||||||
<use xlink:href="#glyph1-22" x="922.726562" y="44"/>
|
<use xlink:href="#glyph1-22" x="971.074219" y="44"/>
|
||||||
<use xlink:href="#glyph1-2" x="925.421875" y="44"/>
|
<use xlink:href="#glyph1-14" x="975.707031" y="44"/>
|
||||||
<use xlink:href="#glyph1-10" x="927.964844" y="44"/>
|
<use xlink:href="#glyph1-13" x="980.628906" y="44"/>
|
||||||
<use xlink:href="#glyph1-16" x="931.101562" y="44"/>
|
|
||||||
<use xlink:href="#glyph1-23" x="935.996094" y="44"/>
|
|
||||||
<use xlink:href="#glyph1-24" x="941.074219" y="44"/>
|
|
||||||
<use xlink:href="#glyph1-25" x="943.960938" y="44"/>
|
|
||||||
<use xlink:href="#glyph1-12" x="946.183594" y="44"/>
|
|
||||||
<use xlink:href="#glyph1-26" x="951.105469" y="44"/>
|
|
||||||
<use xlink:href="#glyph1-12" x="955.839844" y="44"/>
|
|
||||||
<use xlink:href="#glyph1-25" x="960.761719" y="44"/>
|
|
||||||
<use xlink:href="#glyph1-2" x="962.984375" y="44"/>
|
|
||||||
<use xlink:href="#glyph1-20" x="965.527344" y="44"/>
|
|
||||||
<use xlink:href="#glyph1-16" x="969.925781" y="44"/>
|
|
||||||
<use xlink:href="#glyph1-14" x="974.820312" y="44"/>
|
|
||||||
<use xlink:href="#glyph1-12" x="979.898438" y="44"/>
|
|
||||||
<use xlink:href="#glyph1-2" x="984.820312" y="44"/>
|
|
||||||
<use xlink:href="#glyph1-1" x="987.363281" y="44"/>
|
|
||||||
<use xlink:href="#glyph1-9" x="989.585938" y="44"/>
|
|
||||||
<use xlink:href="#glyph1-2" x="993.753906" y="44"/>
|
|
||||||
<use xlink:href="#glyph1-15" x="996.296875" y="44"/>
|
|
||||||
<use xlink:href="#glyph1-1" x="999.113281" y="44"/>
|
|
||||||
<use xlink:href="#glyph1-21" x="1001.335938" y="44"/>
|
|
||||||
<use xlink:href="#glyph1-1" x="1006.40625" y="44"/>
|
|
||||||
<use xlink:href="#glyph1-9" x="1008.628906" y="44"/>
|
|
||||||
<use xlink:href="#glyph1-11" x="1012.796875" y="44"/>
|
|
||||||
<use xlink:href="#glyph1-12" x="1017.867188" y="44"/>
|
|
||||||
<use xlink:href="#glyph1-14" x="1022.789062" y="44"/>
|
|
||||||
</g>
|
</g>
|
||||||
</g>
|
</g>
|
||||||
<path style="fill:none;stroke-width:1;stroke-linecap:butt;stroke-linejoin:miter;stroke:rgb(0%,0%,0%);stroke-opacity:1;stroke-miterlimit:10;" d="M 35.601562 36 L 31.601562 36 L 31.601562 128 L 35.601562 128 "/>
|
<path style="fill:none;stroke-width:1;stroke-linecap:butt;stroke-linejoin:miter;stroke:rgb(0%,0%,0%);stroke-opacity:1;stroke-miterlimit:10;" d="M 46.675781 36 L 42.675781 36 L 42.675781 160 L 46.675781 160 "/>
|
||||||
<path style="fill:none;stroke-width:1;stroke-linecap:butt;stroke-linejoin:miter;stroke:rgb(0%,0%,0%);stroke-opacity:1;stroke-miterlimit:10;" d="M 1057.957031 36 L 1061.957031 36 L 1061.957031 128 L 1057.957031 128 "/>
|
<path style="fill:none;stroke-width:1;stroke-linecap:butt;stroke-linejoin:miter;stroke:rgb(0%,0%,0%);stroke-opacity:1;stroke-miterlimit:10;" d="M 1138.78125 36 L 1142.78125 36 L 1142.78125 160 L 1138.78125 160 "/>
|
||||||
<g style="fill:rgb(0%,0%,0%);fill-opacity:1;">
|
<g style="fill:rgb(0%,0%,0%);fill-opacity:1;">
|
||||||
<use xlink:href="#glyph1-9" x="33.601562" y="44"/>
|
<use xlink:href="#glyph1-6" x="44.675781" y="44"/>
|
||||||
<use xlink:href="#glyph1-27" x="37.769531" y="44"/>
|
<use xlink:href="#glyph1-23" x="48.84375" y="44"/>
|
||||||
<use xlink:href="#glyph1-1" x="44.3125" y="44"/>
|
<use xlink:href="#glyph1-10" x="55.386719" y="44"/>
|
||||||
<use xlink:href="#glyph1-10" x="46.535156" y="44"/>
|
<use xlink:href="#glyph1-7" x="57.609375" y="44"/>
|
||||||
<use xlink:href="#glyph1-20" x="49.671875" y="44"/>
|
<use xlink:href="#glyph1-19" x="60.746094" y="44"/>
|
||||||
<use xlink:href="#glyph1-11" x="54.070312" y="44"/>
|
<use xlink:href="#glyph1-20" x="65.144531" y="44"/>
|
||||||
</g>
|
</g>
|
||||||
<path style="fill:none;stroke-width:1;stroke-linecap:butt;stroke-linejoin:miter;stroke:rgb(0%,0%,0%);stroke-opacity:1;stroke-miterlimit:10;" d="M 1086.320312 49 L 1086.320312 43 "/>
|
<path style="fill:none;stroke-width:1;stroke-linecap:butt;stroke-linejoin:miter;stroke:rgb(0%,0%,0%);stroke-opacity:1;stroke-miterlimit:10;" d="M 1177.296875 49 L 1177.296875 43 "/>
|
||||||
<g clip-path="url(#clip13)" clip-rule="nonzero">
|
<g clip-path="url(#clip13)" clip-rule="nonzero">
|
||||||
<g style="fill:rgb(0%,0%,0%);fill-opacity:1;">
|
<g style="fill:rgb(0%,0%,0%);fill-opacity:1;">
|
||||||
<use xlink:href="#glyph1-19" x="1088.320312" y="44"/>
|
<use xlink:href="#glyph1-24" x="1179.296875" y="44"/>
|
||||||
<use xlink:href="#glyph1-27" x="1093.398438" y="44"/>
|
<use xlink:href="#glyph1-23" x="1184.375" y="44"/>
|
||||||
<use xlink:href="#glyph1-1" x="1099.941406" y="44"/>
|
<use xlink:href="#glyph1-10" x="1190.917969" y="44"/>
|
||||||
<use xlink:href="#glyph1-10" x="1102.164062" y="44"/>
|
<use xlink:href="#glyph1-7" x="1193.140625" y="44"/>
|
||||||
<use xlink:href="#glyph1-20" x="1105.300781" y="44"/>
|
<use xlink:href="#glyph1-19" x="1196.277344" y="44"/>
|
||||||
<use xlink:href="#glyph1-11" x="1109.699219" y="44"/>
|
<use xlink:href="#glyph1-20" x="1200.675781" y="44"/>
|
||||||
<use xlink:href="#glyph1-2" x="1114.769531" y="44"/>
|
<use xlink:href="#glyph1-4" x="1205.746094" y="44"/>
|
||||||
<use xlink:href="#glyph1-1" x="1117.3125" y="44"/>
|
<use xlink:href="#glyph1-10" x="1208.289062" y="44"/>
|
||||||
<use xlink:href="#glyph1-9" x="1119.535156" y="44"/>
|
<use xlink:href="#glyph1-6" x="1210.511719" y="44"/>
|
||||||
<use xlink:href="#glyph1-2" x="1123.703125" y="44"/>
|
<use xlink:href="#glyph1-4" x="1214.679688" y="44"/>
|
||||||
<use xlink:href="#glyph1-15" x="1126.246094" y="44"/>
|
<use xlink:href="#glyph1-21" x="1217.222656" y="44"/>
|
||||||
<use xlink:href="#glyph1-1" x="1129.0625" y="44"/>
|
<use xlink:href="#glyph1-10" x="1220.039062" y="44"/>
|
||||||
<use xlink:href="#glyph1-21" x="1131.285156" y="44"/>
|
<use xlink:href="#glyph1-11" x="1222.261719" y="44"/>
|
||||||
<use xlink:href="#glyph1-1" x="1136.355469" y="44"/>
|
<use xlink:href="#glyph1-10" x="1227.332031" y="44"/>
|
||||||
<use xlink:href="#glyph1-9" x="1138.578125" y="44"/>
|
<use xlink:href="#glyph1-6" x="1229.554688" y="44"/>
|
||||||
<use xlink:href="#glyph1-11" x="1142.746094" y="44"/>
|
<use xlink:href="#glyph1-20" x="1233.722656" y="44"/>
|
||||||
<use xlink:href="#glyph1-12" x="1147.816406" y="44"/>
|
<use xlink:href="#glyph1-14" x="1238.792969" y="44"/>
|
||||||
<use xlink:href="#glyph1-14" x="1152.738281" y="44"/>
|
<use xlink:href="#glyph1-13" x="1243.714844" y="44"/>
|
||||||
</g>
|
</g>
|
||||||
</g>
|
</g>
|
||||||
<path style="fill:none;stroke-width:1;stroke-linecap:butt;stroke-linejoin:miter;stroke:rgb(40%,80%,40%);stroke-opacity:1;stroke-miterlimit:10;" d="M 11.480469 46 L 11.480469 60 "/>
|
<path style="fill:none;stroke-width:1;stroke-linecap:butt;stroke-linejoin:miter;stroke:rgb(40%,80%,40%);stroke-opacity:1;stroke-miterlimit:10;" d="M 10.746094 46 L 10.746094 60 "/>
|
||||||
</g>
|
</g>
|
||||||
</svg>
|
</svg>
|
||||||
|
Before Width: | Height: | Size: 63 KiB After Width: | Height: | Size: 61 KiB |
@ -1,6 +1,7 @@
|
|||||||
(lang dune 3.9)
|
(lang dune 3.9)
|
||||||
(name eio)
|
(name eio)
|
||||||
(formatting disabled)
|
(formatting disabled)
|
||||||
|
(subst disabled)
|
||||||
(generate_opam_files true)
|
(generate_opam_files true)
|
||||||
(source (github ocaml-multicore/eio))
|
(source (github ocaml-multicore/eio))
|
||||||
(license ISC)
|
(license ISC)
|
||||||
@ -13,7 +14,7 @@
|
|||||||
(description "An effect-based IO API for multicore OCaml with fibers.")
|
(description "An effect-based IO API for multicore OCaml with fibers.")
|
||||||
(conflicts (seq (< 0.3)))
|
(conflicts (seq (< 0.3)))
|
||||||
(depends
|
(depends
|
||||||
(ocaml (>= 5.1.0))
|
(ocaml (>= 5.2.0))
|
||||||
(bigstringaf (>= 0.9.0))
|
(bigstringaf (>= 0.9.0))
|
||||||
(cstruct (>= 6.0.1))
|
(cstruct (>= 6.0.1))
|
||||||
lwt-dllist
|
lwt-dllist
|
||||||
@ -48,6 +49,7 @@
|
|||||||
(eio (= :version))
|
(eio (= :version))
|
||||||
(iomux (>= 0.2))
|
(iomux (>= 0.2))
|
||||||
(mdx (and (>= 2.4.1) :with-test))
|
(mdx (and (>= 2.4.1) :with-test))
|
||||||
|
(conf-bash :with-test)
|
||||||
(fmt (>= 0.8.9))))
|
(fmt (>= 0.8.9))))
|
||||||
(package
|
(package
|
||||||
(name eio_windows)
|
(name eio_windows)
|
||||||
|
3
eio.opam
3
eio.opam
@ -10,7 +10,7 @@ doc: "https://ocaml-multicore.github.io/eio/"
|
|||||||
bug-reports: "https://github.com/ocaml-multicore/eio/issues"
|
bug-reports: "https://github.com/ocaml-multicore/eio/issues"
|
||||||
depends: [
|
depends: [
|
||||||
"dune" {>= "3.9"}
|
"dune" {>= "3.9"}
|
||||||
"ocaml" {>= "5.1.0"}
|
"ocaml" {>= "5.2.0"}
|
||||||
"bigstringaf" {>= "0.9.0"}
|
"bigstringaf" {>= "0.9.0"}
|
||||||
"cstruct" {>= "6.0.1"}
|
"cstruct" {>= "6.0.1"}
|
||||||
"lwt-dllist"
|
"lwt-dllist"
|
||||||
@ -29,7 +29,6 @@ conflicts: [
|
|||||||
"seq" {< "0.3"}
|
"seq" {< "0.3"}
|
||||||
]
|
]
|
||||||
build: [
|
build: [
|
||||||
["dune" "subst"] {dev}
|
|
||||||
[
|
[
|
||||||
"dune"
|
"dune"
|
||||||
"build"
|
"build"
|
||||||
|
@ -20,7 +20,6 @@ depends: [
|
|||||||
"odoc" {with-doc}
|
"odoc" {with-doc}
|
||||||
]
|
]
|
||||||
build: [
|
build: [
|
||||||
["dune" "subst"] {dev}
|
|
||||||
[
|
[
|
||||||
"dune"
|
"dune"
|
||||||
"build"
|
"build"
|
||||||
|
@ -21,7 +21,6 @@ depends: [
|
|||||||
"odoc" {with-doc}
|
"odoc" {with-doc}
|
||||||
]
|
]
|
||||||
build: [
|
build: [
|
||||||
["dune" "subst"] {dev}
|
|
||||||
[
|
[
|
||||||
"dune"
|
"dune"
|
||||||
"build"
|
"build"
|
||||||
|
@ -13,11 +13,11 @@ depends: [
|
|||||||
"eio" {= version}
|
"eio" {= version}
|
||||||
"iomux" {>= "0.2"}
|
"iomux" {>= "0.2"}
|
||||||
"mdx" {>= "2.4.1" & with-test}
|
"mdx" {>= "2.4.1" & with-test}
|
||||||
|
"conf-bash" {with-test}
|
||||||
"fmt" {>= "0.8.9"}
|
"fmt" {>= "0.8.9"}
|
||||||
"odoc" {with-doc}
|
"odoc" {with-doc}
|
||||||
]
|
]
|
||||||
build: [
|
build: [
|
||||||
["dune" "subst"] {dev}
|
|
||||||
[
|
[
|
||||||
"dune"
|
"dune"
|
||||||
"build"
|
"build"
|
||||||
|
@ -17,7 +17,6 @@ depends: [
|
|||||||
"odoc" {with-doc}
|
"odoc" {with-doc}
|
||||||
]
|
]
|
||||||
build: [
|
build: [
|
||||||
["dune" "subst"] {dev}
|
|
||||||
[
|
[
|
||||||
"dune"
|
"dune"
|
||||||
"build"
|
"build"
|
||||||
|
@ -1,21 +1,32 @@
|
|||||||
(* Walks the directory tree rooted at the current directory,
|
(* Walk the directory tree rooted at the current directory,
|
||||||
displaying all directory names (skipping hidden directories and `_build`). *)
|
showing a summary for any .mli files. *)
|
||||||
|
|
||||||
open Eio.Std
|
|
||||||
|
|
||||||
let ( / ) = Eio.Path.( / )
|
let ( / ) = Eio.Path.( / )
|
||||||
|
|
||||||
let rec scan t =
|
let is_doc_comment = String.starts_with ~prefix:"(** "
|
||||||
|
|
||||||
|
(* Print the first line of [t]'s doc-comment, if any *)
|
||||||
|
let scan_mli t f =
|
||||||
|
Eio.Path.with_lines t (fun lines ->
|
||||||
|
Seq.find is_doc_comment lines
|
||||||
|
|> Option.iter (fun line ->
|
||||||
|
let stop = String.index_from_opt line 4 '*' |> Option.value ~default:(String.length line) in
|
||||||
|
Format.fprintf f "%a: %s@." Eio.Path.pp t (String.sub line 4 (stop - 4))
|
||||||
|
)
|
||||||
|
)
|
||||||
|
|
||||||
|
(* Walk the tree rooted at [t] and scan any .mli files found. *)
|
||||||
|
let rec scan t f =
|
||||||
match Eio.Path.kind ~follow:false t with
|
match Eio.Path.kind ~follow:false t with
|
||||||
| `Directory ->
|
| `Directory ->
|
||||||
traceln "Visiting %a" Eio.Path.pp t;
|
|
||||||
Eio.Path.read_dir t |> List.iter (function
|
Eio.Path.read_dir t |> List.iter (function
|
||||||
| "_build" -> ()
|
| "_build" | "_opam" -> () (* Don't examine these directories *)
|
||||||
| item when String.starts_with ~prefix:"." item -> ()
|
| item when String.starts_with ~prefix:"." item -> () (* Skip hidden items *)
|
||||||
| item -> scan (t / item)
|
| item -> scan (t / item) f
|
||||||
)
|
)
|
||||||
|
| `Regular_file when Filename.check_suffix (snd t) ".mli" -> scan_mli t f
|
||||||
| _ -> ()
|
| _ -> ()
|
||||||
|
|
||||||
let () =
|
let () =
|
||||||
Eio_main.run @@ fun env ->
|
Eio_main.run @@ fun env ->
|
||||||
scan (Eio.Stdenv.cwd env)
|
scan (Eio.Stdenv.cwd env) Format.std_formatter
|
||||||
|
@ -218,6 +218,13 @@ val seq : ?stop:bool parser -> 'a parser -> 'a Seq.t parser
|
|||||||
It is not necessary to consume all the elements of the
|
It is not necessary to consume all the elements of the
|
||||||
sequence.
|
sequence.
|
||||||
|
|
||||||
|
Example ([head 4] is a parser that takes 4 lines):
|
||||||
|
|
||||||
|
{[
|
||||||
|
let head n r =
|
||||||
|
r |> Buf_read.(seq line) |> Seq.take n |> List.of_seq
|
||||||
|
]}
|
||||||
|
|
||||||
@param stop This is used before parsing each item.
|
@param stop This is used before parsing each item.
|
||||||
The sequence ends if this returns [true].
|
The sequence ends if this returns [true].
|
||||||
The default is {!at_end_of_input}. *)
|
The default is {!at_end_of_input}. *)
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
(library
|
(library
|
||||||
(name eio__core)
|
(name eio__core)
|
||||||
(public_name eio.core)
|
(public_name eio.core)
|
||||||
(libraries cstruct hmap lwt-dllist fmt optint domain-local-await eio.runtime_events))
|
(libraries hmap lwt-dllist fmt optint eio.runtime_events))
|
||||||
|
@ -7,6 +7,7 @@ module Private = struct
|
|||||||
module Suspend = Suspend
|
module Suspend = Suspend
|
||||||
module Cells = Cells
|
module Cells = Cells
|
||||||
module Broadcast = Broadcast
|
module Broadcast = Broadcast
|
||||||
|
module Single_waiter = Single_waiter
|
||||||
module Trace = Trace
|
module Trace = Trace
|
||||||
module Fiber_context = Cancel.Fiber_context
|
module Fiber_context = Cancel.Fiber_context
|
||||||
module Debug = Debug
|
module Debug = Debug
|
||||||
@ -18,6 +19,4 @@ module Private = struct
|
|||||||
| Fork = Fiber.Fork
|
| Fork = Fiber.Fork
|
||||||
| Get_context = Cancel.Get_context
|
| Get_context = Cancel.Get_context
|
||||||
end
|
end
|
||||||
|
|
||||||
module Dla = Dla
|
|
||||||
end
|
end
|
||||||
|
@ -606,6 +606,7 @@ module Private : sig
|
|||||||
|
|
||||||
module Cells = Cells
|
module Cells = Cells
|
||||||
module Broadcast = Broadcast
|
module Broadcast = Broadcast
|
||||||
|
module Single_waiter = Single_waiter
|
||||||
|
|
||||||
(** Every fiber has an associated context. *)
|
(** Every fiber has an associated context. *)
|
||||||
module Fiber_context : sig
|
module Fiber_context : sig
|
||||||
@ -781,8 +782,4 @@ module Private : sig
|
|||||||
val v : t
|
val v : t
|
||||||
(** Backends should use this for {!Eio.Stdenv.debug}. *)
|
(** Backends should use this for {!Eio.Stdenv.debug}. *)
|
||||||
end
|
end
|
||||||
|
|
||||||
module Dla : sig
|
|
||||||
val prepare_for_await : unit -> Domain_local_await.t
|
|
||||||
end
|
|
||||||
end
|
end
|
||||||
|
@ -39,7 +39,8 @@ let fork_daemon ~sw f =
|
|||||||
(* The daemon was cancelled because all non-daemon fibers are finished. *)
|
(* The daemon was cancelled because all non-daemon fibers are finished. *)
|
||||||
()
|
()
|
||||||
| exception ex ->
|
| exception ex ->
|
||||||
Switch.fail sw ex; (* The [with_daemon] ensures this will succeed *)
|
let bt = Printexc.get_raw_backtrace () in
|
||||||
|
Switch.fail ~bt sw ex; (* The [with_daemon] ensures this will succeed *)
|
||||||
) (* else the fiber should report the error to [sw], but [sw] is failed anyway *)
|
) (* else the fiber should report the error to [sw], but [sw] is failed anyway *)
|
||||||
|
|
||||||
let fork_promise ~sw f =
|
let fork_promise ~sw f =
|
||||||
@ -65,7 +66,8 @@ let fork_promise_exn ~sw f =
|
|||||||
match Switch.with_op sw f with
|
match Switch.with_op sw f with
|
||||||
| x -> Promise.resolve r x
|
| x -> Promise.resolve r x
|
||||||
| exception ex ->
|
| exception ex ->
|
||||||
Switch.fail sw ex (* The [with_op] ensures this will succeed *)
|
let bt = Printexc.get_raw_backtrace () in
|
||||||
|
Switch.fail ~bt sw ex (* The [with_op] ensures this will succeed *)
|
||||||
);
|
);
|
||||||
p
|
p
|
||||||
|
|
||||||
@ -226,7 +228,7 @@ module List = struct
|
|||||||
|
|
||||||
let release t =
|
let release t =
|
||||||
t.free_fibers <- t.free_fibers + 1;
|
t.free_fibers <- t.free_fibers + 1;
|
||||||
if t.free_fibers = 1 then Single_waiter.wake t.cond (Ok ())
|
if t.free_fibers = 1 then Single_waiter.wake_if_sleeping t.cond
|
||||||
|
|
||||||
let use t fn x =
|
let use t fn x =
|
||||||
await_free t;
|
await_free t;
|
||||||
|
@ -1,25 +1,32 @@
|
|||||||
(* Allows a single fiber to wait to be notified by another fiber in the same domain.
|
type 'a state =
|
||||||
If multiple fibers need to wait at once, or the notification comes from another domain,
|
| Running
|
||||||
this can't be used. *)
|
| Sleeping of (('a, exn) result -> unit)
|
||||||
|
|
||||||
type 'a t = {
|
type 'a t = 'a state ref
|
||||||
mutable wake : ('a, exn) result -> unit;
|
|
||||||
}
|
|
||||||
|
|
||||||
let create () = { wake = ignore }
|
let create () = ref Running
|
||||||
|
|
||||||
let wake t v = t.wake v
|
let wake t v =
|
||||||
|
match !t with
|
||||||
|
| Running -> false
|
||||||
|
| Sleeping fn ->
|
||||||
|
t := Running;
|
||||||
|
fn v;
|
||||||
|
true
|
||||||
|
|
||||||
|
let wake_if_sleeping t =
|
||||||
|
ignore (wake t (Ok ()) : bool)
|
||||||
|
|
||||||
let await t op id =
|
let await t op id =
|
||||||
let x =
|
let x =
|
||||||
Suspend.enter op @@ fun ctx enqueue ->
|
Suspend.enter op @@ fun ctx enqueue ->
|
||||||
Cancel.Fiber_context.set_cancel_fn ctx (fun ex ->
|
Cancel.Fiber_context.set_cancel_fn ctx (fun ex ->
|
||||||
t.wake <- ignore;
|
t := Running;
|
||||||
enqueue (Error ex)
|
enqueue (Error ex)
|
||||||
);
|
);
|
||||||
t.wake <- (fun x ->
|
t := Sleeping (fun x ->
|
||||||
Cancel.Fiber_context.clear_cancel_fn ctx;
|
Cancel.Fiber_context.clear_cancel_fn ctx;
|
||||||
t.wake <- ignore;
|
t := Running;
|
||||||
enqueue x
|
enqueue x
|
||||||
)
|
)
|
||||||
in
|
in
|
||||||
@ -29,7 +36,7 @@ let await t op id =
|
|||||||
let await_protect t op id =
|
let await_protect t op id =
|
||||||
let x =
|
let x =
|
||||||
Suspend.enter_unchecked op @@ fun _ctx enqueue ->
|
Suspend.enter_unchecked op @@ fun _ctx enqueue ->
|
||||||
t.wake <- (fun x -> t.wake <- ignore; enqueue x)
|
t := Sleeping (fun x -> t := Running; enqueue x)
|
||||||
in
|
in
|
||||||
Trace.get id;
|
Trace.get id;
|
||||||
x
|
x
|
||||||
|
25
lib_eio/core/single_waiter.mli
Normal file
25
lib_eio/core/single_waiter.mli
Normal file
@ -0,0 +1,25 @@
|
|||||||
|
(** Allows a single fiber to wait to be notified by another fiber in the same domain.
|
||||||
|
If multiple fibers need to wait at once, or the notification comes from another domain,
|
||||||
|
this can't be used. *)
|
||||||
|
|
||||||
|
type 'a t
|
||||||
|
(** A handle representing a fiber that might be sleeping.
|
||||||
|
It is either in the Running or Sleeping state. *)
|
||||||
|
|
||||||
|
val create : unit -> 'a t
|
||||||
|
(** [create ()] is a new waiter, initially in the Running state. *)
|
||||||
|
|
||||||
|
val wake : 'a t -> ('a, exn) result -> bool
|
||||||
|
(** [wake t v] resumes [t]'s fiber with value [v] and returns [true] if it was sleeping.
|
||||||
|
If [t] is Running then this just returns [false]. *)
|
||||||
|
|
||||||
|
val wake_if_sleeping : unit t -> unit
|
||||||
|
(** [wake_if_sleeping] is [ignore (wake t (Ok ()))]. *)
|
||||||
|
|
||||||
|
val await : 'a t -> string -> Trace.id -> 'a
|
||||||
|
(** [await t op id] suspends the calling fiber, changing [t]'s state to Sleeping.
|
||||||
|
If the fiber is cancelled, a cancel exception is raised.
|
||||||
|
[op] and [id] are used for tracing. *)
|
||||||
|
|
||||||
|
val await_protect : 'a t -> string -> Trace.id -> 'a
|
||||||
|
(** [await_protect] is like {!await}, but the sleep cannot be cancelled. *)
|
@ -72,7 +72,7 @@ let dec_fibers t =
|
|||||||
if t.daemon_fibers > 0 && t.fibers = t.daemon_fibers then
|
if t.daemon_fibers > 0 && t.fibers = t.daemon_fibers then
|
||||||
Cancel.cancel t.cancel Exit;
|
Cancel.cancel t.cancel Exit;
|
||||||
if t.fibers = 0 then
|
if t.fibers = 0 then
|
||||||
Single_waiter.wake t.waiter (Ok ())
|
Single_waiter.wake_if_sleeping t.waiter
|
||||||
|
|
||||||
let with_op t fn =
|
let with_op t fn =
|
||||||
inc_fibers t;
|
inc_fibers t;
|
||||||
|
@ -105,7 +105,7 @@ let run_full main =
|
|||||||
let result = ref None in
|
let result = ref None in
|
||||||
let `Exit_scheduler =
|
let `Exit_scheduler =
|
||||||
Domain_local_await.using
|
Domain_local_await.using
|
||||||
~prepare_for_await:Eio.Private.Dla.prepare_for_await
|
~prepare_for_await:Eio_utils.Dla.prepare_for_await
|
||||||
~while_running:(fun () ->
|
~while_running:(fun () ->
|
||||||
fork ~new_fiber (fun () -> result := Some (main stdenv))) in
|
fork ~new_fiber (fun () -> result := Some (main stdenv))) in
|
||||||
match !result with
|
match !result with
|
||||||
|
@ -231,6 +231,9 @@ val run_server :
|
|||||||
In such cases you must ensure that [connection_handler] only accesses thread-safe values.
|
In such cases you must ensure that [connection_handler] only accesses thread-safe values.
|
||||||
Note that having more than {!Domain.recommended_domain_count} domains in total is likely to result in bad performance.
|
Note that having more than {!Domain.recommended_domain_count} domains in total is likely to result in bad performance.
|
||||||
|
|
||||||
|
For services that are bottlenecked on CPU rather than IO,
|
||||||
|
you can run a single accept loop and have the handler submit CPU-intensive jobs to an {!module:Executor_pool}.
|
||||||
|
|
||||||
@param max_connections The maximum number of concurrent connections accepted by [s] at any time.
|
@param max_connections The maximum number of concurrent connections accepted by [s] at any time.
|
||||||
The default is [Int.max_int].
|
The default is [Int.max_int].
|
||||||
@param stop Resolving this promise causes [s] to stop accepting new connections.
|
@param stop Resolving this promise causes [s] to stop accepting new connections.
|
||||||
|
@ -1,11 +1,22 @@
|
|||||||
type 'a t = 'a Fs.dir * Fs.path
|
type 'a t = 'a Fs.dir * Fs.path
|
||||||
|
|
||||||
|
(* Like [Filename.is_relative] but always using "/" as the separator. *)
|
||||||
|
let is_relative = function
|
||||||
|
| "" -> true
|
||||||
|
| x -> x.[0] <> '/'
|
||||||
|
|
||||||
|
(* Like [Filename.concat] but always using "/" as the separator. *)
|
||||||
|
let concat a b =
|
||||||
|
let l = String.length a in
|
||||||
|
if l = 0 || a.[l - 1] = '/' then a ^ b
|
||||||
|
else a ^ "/" ^ b
|
||||||
|
|
||||||
let ( / ) (dir, p1) p2 =
|
let ( / ) (dir, p1) p2 =
|
||||||
match p1, p2 with
|
match p1, p2 with
|
||||||
| p1, "" -> (dir, Filename.concat p1 p2)
|
| p1, "" -> (dir, concat p1 p2)
|
||||||
| _, p2 when not (Filename.is_relative p2) -> (dir, p2)
|
| _, p2 when not (is_relative p2) -> (dir, p2)
|
||||||
| ".", p2 -> (dir, p2)
|
| ".", p2 -> (dir, p2)
|
||||||
| p1, p2 -> (dir, Filename.concat p1 p2)
|
| p1, p2 -> (dir, concat p1 p2)
|
||||||
|
|
||||||
let pp f (Resource.T (t, ops), p) =
|
let pp f (Resource.T (t, ops), p) =
|
||||||
let module X = (val (Resource.get ops Fs.Pi.Dir)) in
|
let module X = (val (Resource.get ops Fs.Pi.Dir)) in
|
||||||
|
@ -1,3 +1,7 @@
|
|||||||
|
type error = ECONNRESET
|
||||||
|
|
||||||
|
exception Unix_error of error * string * string
|
||||||
|
|
||||||
type file_descr = [`Open | `Closed] Atomic.t
|
type file_descr = [`Open | `Closed] Atomic.t
|
||||||
|
|
||||||
let make () = Atomic.make `Open
|
let make () = Atomic.make `Open
|
||||||
|
@ -1,6 +1,7 @@
|
|||||||
(library
|
(library
|
||||||
(name eio_unix)
|
(name eio_unix)
|
||||||
(public_name eio.unix)
|
(public_name eio.unix)
|
||||||
|
(public_headers include/fork_action.h)
|
||||||
(foreign_stubs
|
(foreign_stubs
|
||||||
(language c)
|
(language c)
|
||||||
(include_dirs include)
|
(include_dirs include)
|
||||||
|
@ -68,9 +68,9 @@ type _ Effect.t +=
|
|||||||
| Socketpair_datagram : Switch.t * Unix.socket_domain * int ->
|
| Socketpair_datagram : Switch.t * Unix.socket_domain * int ->
|
||||||
([`Unix_fd | datagram_socket_ty] r * [`Unix_fd | datagram_socket_ty] r) Effect.t
|
([`Unix_fd | datagram_socket_ty] r * [`Unix_fd | datagram_socket_ty] r) Effect.t
|
||||||
|
|
||||||
let open_stream s = (s : _ stream_socket :> [< `Unix_fd | stream_socket_ty] r)
|
let open_stream s = (s : [`Unix_fd | stream_socket_ty] r :> [< `Unix_fd | stream_socket_ty] r)
|
||||||
let open_listening s = (s : _ listening_socket :> [< `Unix_fd | listening_socket_ty] r)
|
let open_listening s = (s : [`Unix_fd | listening_socket_ty] r :> [< `Unix_fd | listening_socket_ty] r)
|
||||||
let open_datagram s = (s : _ datagram_socket :> [< `Unix_fd | datagram_socket_ty] r)
|
let open_datagram s = (s : [`Unix_fd | datagram_socket_ty] r :> [< `Unix_fd | datagram_socket_ty] r)
|
||||||
|
|
||||||
let import_socket_stream ~sw ~close_unix fd =
|
let import_socket_stream ~sw ~close_unix fd =
|
||||||
open_stream @@ Effect.perform (Import_socket_stream (sw, close_unix, fd))
|
open_stream @@ Effect.perform (Import_socket_stream (sw, close_unix, fd))
|
||||||
@ -86,7 +86,8 @@ let socketpair_stream ~sw ?(domain=Unix.PF_UNIX) ?(protocol=0) () =
|
|||||||
(open_stream a, open_stream b)
|
(open_stream a, open_stream b)
|
||||||
|
|
||||||
let socketpair_datagram ~sw ?(domain=Unix.PF_UNIX) ?(protocol=0) () =
|
let socketpair_datagram ~sw ?(domain=Unix.PF_UNIX) ?(protocol=0) () =
|
||||||
Effect.perform (Socketpair_datagram (sw, domain, protocol))
|
let a, b = Effect.perform (Socketpair_datagram (sw, domain, protocol)) in
|
||||||
|
(open_datagram a, open_datagram b)
|
||||||
|
|
||||||
let fd socket =
|
let fd socket =
|
||||||
Option.get (Resource.fd_opt socket)
|
Option.get (Resource.fd_opt socket)
|
||||||
|
@ -55,7 +55,7 @@ end
|
|||||||
|
|
||||||
(** {2 Creating or importing sockets} *)
|
(** {2 Creating or importing sockets} *)
|
||||||
|
|
||||||
val import_socket_stream : sw:Switch.t -> close_unix:bool -> Unix.file_descr -> [`Unix_fd | stream_socket_ty] r
|
val import_socket_stream : sw:Switch.t -> close_unix:bool -> Unix.file_descr -> [< `Unix_fd | stream_socket_ty] r
|
||||||
(** [import_socket_stream ~sw ~close_unix fd] is an Eio flow that uses [fd].
|
(** [import_socket_stream ~sw ~close_unix fd] is an Eio flow that uses [fd].
|
||||||
|
|
||||||
It can be cast to e.g. {!source} for a one-way flow.
|
It can be cast to e.g. {!source} for a one-way flow.
|
||||||
@ -63,14 +63,14 @@ val import_socket_stream : sw:Switch.t -> close_unix:bool -> Unix.file_descr ->
|
|||||||
|
|
||||||
The [close_unix] and [sw] arguments are passed to {!Fd.of_unix}. *)
|
The [close_unix] and [sw] arguments are passed to {!Fd.of_unix}. *)
|
||||||
|
|
||||||
val import_socket_listening : sw:Switch.t -> close_unix:bool -> Unix.file_descr -> [`Unix_fd | listening_socket_ty] r
|
val import_socket_listening : sw:Switch.t -> close_unix:bool -> Unix.file_descr -> [< `Unix_fd | listening_socket_ty] r
|
||||||
(** [import_socket_listening ~sw ~close_unix fd] is an Eio listening socket that uses [fd].
|
(** [import_socket_listening ~sw ~close_unix fd] is an Eio listening socket that uses [fd].
|
||||||
|
|
||||||
The socket object will be closed when [sw] finishes.
|
The socket object will be closed when [sw] finishes.
|
||||||
|
|
||||||
The [close_unix] and [sw] arguments are passed to {!Fd.of_unix}. *)
|
The [close_unix] and [sw] arguments are passed to {!Fd.of_unix}. *)
|
||||||
|
|
||||||
val import_socket_datagram : sw:Switch.t -> close_unix:bool -> Unix.file_descr -> [`Unix_fd | datagram_socket_ty] r
|
val import_socket_datagram : sw:Switch.t -> close_unix:bool -> Unix.file_descr -> [< `Unix_fd | datagram_socket_ty] r
|
||||||
(** [import_socket_datagram ~sw ~close_unix fd] is an Eio datagram socket that uses [fd].
|
(** [import_socket_datagram ~sw ~close_unix fd] is an Eio datagram socket that uses [fd].
|
||||||
|
|
||||||
The socket object will be closed when [sw] finishes.
|
The socket object will be closed when [sw] finishes.
|
||||||
@ -82,7 +82,7 @@ val socketpair_stream :
|
|||||||
?domain:Unix.socket_domain ->
|
?domain:Unix.socket_domain ->
|
||||||
?protocol:int ->
|
?protocol:int ->
|
||||||
unit ->
|
unit ->
|
||||||
[`Unix_fd | stream_socket_ty] r * [`Unix_fd | stream_socket_ty] r
|
[< `Unix_fd | stream_socket_ty] r * [< `Unix_fd | stream_socket_ty] r
|
||||||
(** [socketpair_stream ~sw ()] returns a connected pair of flows, such that writes to one can be read by the other.
|
(** [socketpair_stream ~sw ()] returns a connected pair of flows, such that writes to one can be read by the other.
|
||||||
|
|
||||||
This creates OS-level resources using [socketpair(2)].
|
This creates OS-level resources using [socketpair(2)].
|
||||||
@ -93,7 +93,7 @@ val socketpair_datagram :
|
|||||||
?domain:Unix.socket_domain ->
|
?domain:Unix.socket_domain ->
|
||||||
?protocol:int ->
|
?protocol:int ->
|
||||||
unit ->
|
unit ->
|
||||||
[`Unix_fd | datagram_socket_ty] r * [`Unix_fd | datagram_socket_ty] r
|
[< `Unix_fd | datagram_socket_ty] r * [< `Unix_fd | datagram_socket_ty] r
|
||||||
(** [socketpair_datagram ~sw ()] returns a connected pair of flows, such that writes to one can be read by the other.
|
(** [socketpair_datagram ~sw ()] returns a connected pair of flows, such that writes to one can be read by the other.
|
||||||
|
|
||||||
This creates OS-level resources using [socketpair(2)].
|
This creates OS-level resources using [socketpair(2)].
|
||||||
|
@ -98,7 +98,13 @@ let get t =
|
|||||||
None
|
None
|
||||||
|
|
||||||
let close_fd fd =
|
let close_fd fd =
|
||||||
Eio.Private.Trace.with_span "close" (fun () -> Unix.close fd)
|
Eio.Private.Trace.with_span "close" (fun () ->
|
||||||
|
try
|
||||||
|
Unix.close fd
|
||||||
|
with Unix.Unix_error (ECONNRESET, _, _) ->
|
||||||
|
(* For FreeBSD. See https://github.com/ocaml-multicore/eio/issues/786 *)
|
||||||
|
()
|
||||||
|
)
|
||||||
|
|
||||||
(* Note: we could simplify this a bit by incrementing [t.ops], as [remove] does.
|
(* Note: we could simplify this a bit by incrementing [t.ops], as [remove] does.
|
||||||
However, that makes dscheck too slow. *)
|
However, that makes dscheck too slow. *)
|
||||||
|
@ -7,10 +7,10 @@ let prepare_for_await () =
|
|||||||
| _ -> ()
|
| _ -> ()
|
||||||
and await () =
|
and await () =
|
||||||
if Atomic.get state != `Released then
|
if Atomic.get state != `Released then
|
||||||
Suspend.enter "domain-local-await" @@ fun ctx enqueue ->
|
Eio.Private.Suspend.enter "domain-local-await" @@ fun ctx enqueue ->
|
||||||
let awaiting = `Awaiting enqueue in
|
let awaiting = `Awaiting enqueue in
|
||||||
if Atomic.compare_and_set state `Init awaiting then (
|
if Atomic.compare_and_set state `Init awaiting then (
|
||||||
Cancel.Fiber_context.set_cancel_fn ctx (fun ex ->
|
Eio.Private.Fiber_context.set_cancel_fn ctx (fun ex ->
|
||||||
if Atomic.compare_and_set state awaiting `Released then (
|
if Atomic.compare_and_set state awaiting `Released then (
|
||||||
enqueue (Error ex)
|
enqueue (Error ex)
|
||||||
)
|
)
|
1
lib_eio/utils/dla.mli
Normal file
1
lib_eio/utils/dla.mli
Normal file
@ -0,0 +1 @@
|
|||||||
|
val prepare_for_await : unit -> Domain_local_await.t
|
@ -1,4 +1,4 @@
|
|||||||
(library
|
(library
|
||||||
(name eio_utils)
|
(name eio_utils)
|
||||||
(public_name eio.utils)
|
(public_name eio.utils)
|
||||||
(libraries eio psq fmt optint))
|
(libraries eio psq fmt optint domain-local-await))
|
||||||
|
@ -5,3 +5,4 @@
|
|||||||
module Lf_queue = Lf_queue
|
module Lf_queue = Lf_queue
|
||||||
module Suspended = Suspended
|
module Suspended = Suspended
|
||||||
module Zzz = Zzz
|
module Zzz = Zzz
|
||||||
|
module Dla = Dla
|
||||||
|
@ -39,7 +39,11 @@
|
|||||||
#ifndef SYS_clone3
|
#ifndef SYS_clone3
|
||||||
# define SYS_clone3 435
|
# define SYS_clone3 435
|
||||||
# define CLONE_PIDFD 0x00001000
|
# define CLONE_PIDFD 0x00001000
|
||||||
struct clone_args {
|
#endif
|
||||||
|
|
||||||
|
// struct clone_args isn't defined in linux-lts headers, so define it here
|
||||||
|
// Note that this struct is versioned by size. See linux/sched.h for details
|
||||||
|
struct caml_eio_clone_args {
|
||||||
uint64_t flags;
|
uint64_t flags;
|
||||||
uint64_t pidfd;
|
uint64_t pidfd;
|
||||||
uint64_t child_tid;
|
uint64_t child_tid;
|
||||||
@ -48,11 +52,7 @@ struct clone_args {
|
|||||||
uint64_t stack;
|
uint64_t stack;
|
||||||
uint64_t stack_size;
|
uint64_t stack_size;
|
||||||
uint64_t tls;
|
uint64_t tls;
|
||||||
uint64_t set_tid;
|
|
||||||
uint64_t set_tid_size;
|
|
||||||
uint64_t cgroup;
|
|
||||||
};
|
};
|
||||||
#endif
|
|
||||||
|
|
||||||
// Make sure we have enough space for at least one entry.
|
// Make sure we have enough space for at least one entry.
|
||||||
#define DIRENT_BUF_SIZE (PATH_MAX + sizeof(struct dirent64))
|
#define DIRENT_BUF_SIZE (PATH_MAX + sizeof(struct dirent64))
|
||||||
@ -178,9 +178,9 @@ static int pidfd_open(pid_t pid, unsigned int flags) {
|
|||||||
|
|
||||||
/* Like clone3, but falls back to fork if not supported.
|
/* Like clone3, but falls back to fork if not supported.
|
||||||
Also, raises exceptions rather then returning an error. */
|
Also, raises exceptions rather then returning an error. */
|
||||||
static pid_t clone3_with_fallback(struct clone_args *cl_args) {
|
static pid_t clone3_with_fallback(struct caml_eio_clone_args *cl_args) {
|
||||||
int *pidfd = (int *)(uintptr_t) cl_args->pidfd;
|
int *pidfd = (int *)(uintptr_t) cl_args->pidfd;
|
||||||
pid_t child_pid = syscall(SYS_clone3, cl_args, sizeof(struct clone_args));
|
pid_t child_pid = syscall(SYS_clone3, cl_args, sizeof(struct caml_eio_clone_args));
|
||||||
|
|
||||||
if (child_pid >= 0)
|
if (child_pid >= 0)
|
||||||
return child_pid; /* Success! */
|
return child_pid; /* Success! */
|
||||||
@ -216,7 +216,7 @@ CAMLprim value caml_eio_clone3(value v_errors, value v_actions) {
|
|||||||
CAMLlocal1(v_result);
|
CAMLlocal1(v_result);
|
||||||
pid_t child_pid;
|
pid_t child_pid;
|
||||||
int pidfd = -1; /* Is automatically close-on-exec */
|
int pidfd = -1; /* Is automatically close-on-exec */
|
||||||
struct clone_args cl_args = {
|
struct caml_eio_clone_args cl_args = {
|
||||||
.flags = CLONE_PIDFD,
|
.flags = CLONE_PIDFD,
|
||||||
.pidfd = (uintptr_t) &pidfd,
|
.pidfd = (uintptr_t) &pidfd,
|
||||||
.exit_signal = SIGCHLD, /* Needed for wait4 to work if we exit before exec */
|
.exit_signal = SIGCHLD, /* Needed for wait4 to work if we exit before exec */
|
||||||
|
@ -207,11 +207,39 @@ let write ?file_offset:off fd buf len =
|
|||||||
raise @@ Err.wrap (Uring.error_of_errno res) "write" ""
|
raise @@ Err.wrap (Uring.error_of_errno res) "write" ""
|
||||||
)
|
)
|
||||||
|
|
||||||
let alloc_fixed () = Effect.perform Sched.Alloc
|
let alloc_fixed () =
|
||||||
|
let s = Sched.get () in
|
||||||
|
match s.mem with
|
||||||
|
| None -> None
|
||||||
|
| Some mem ->
|
||||||
|
match Uring.Region.alloc mem with
|
||||||
|
| buf -> Some buf
|
||||||
|
| exception Uring.Region.No_space -> None
|
||||||
|
|
||||||
let alloc_fixed_or_wait () = Effect.perform Sched.Alloc_or_wait
|
let alloc_fixed_or_wait () =
|
||||||
|
let s = Sched.get () in
|
||||||
|
match s.mem with
|
||||||
|
| None -> failwith "No fixed buffer available"
|
||||||
|
| Some mem ->
|
||||||
|
match Uring.Region.alloc mem with
|
||||||
|
| buf -> buf
|
||||||
|
| exception Uring.Region.No_space ->
|
||||||
|
let id = Eio.Private.Trace.mint_id () in
|
||||||
|
let trigger = Eio.Private.Single_waiter.create () in
|
||||||
|
let node = Lwt_dllist.add_r trigger s.mem_q in
|
||||||
|
try
|
||||||
|
Eio.Private.Single_waiter.await trigger "alloc_fixed_or_wait" id
|
||||||
|
with ex ->
|
||||||
|
Lwt_dllist.remove node;
|
||||||
|
raise ex
|
||||||
|
|
||||||
let free_fixed buf = Effect.perform (Sched.Free buf)
|
let rec free_fixed buf =
|
||||||
|
let s = Sched.get () in
|
||||||
|
match Lwt_dllist.take_opt_l s.mem_q with
|
||||||
|
| None -> Uring.Region.free buf
|
||||||
|
| Some k ->
|
||||||
|
if not (Eio.Private.Single_waiter.wake k (Ok buf)) then
|
||||||
|
free_fixed buf (* [k] was already cancelled, but not yet removed from the queue *)
|
||||||
|
|
||||||
let splice src ~dst ~len =
|
let splice src ~dst ~len =
|
||||||
Fd.use_exn "splice-src" src @@ fun src ->
|
Fd.use_exn "splice-src" src @@ fun src ->
|
||||||
@ -571,7 +599,10 @@ module Process = struct
|
|||||||
let exit_status, set_exit_status = Promise.create () in
|
let exit_status, set_exit_status = Promise.create () in
|
||||||
let t =
|
let t =
|
||||||
Fd.use_exn "errors-w" errors_w @@ fun errors_w ->
|
Fd.use_exn "errors-w" errors_w @@ fun errors_w ->
|
||||||
let pid, pid_fd = eio_spawn errors_w c_actions in
|
let pid, pid_fd =
|
||||||
|
Eio.Private.Trace.with_span "spawn" @@ fun () ->
|
||||||
|
eio_spawn errors_w c_actions
|
||||||
|
in
|
||||||
let pid_fd = Fd.of_unix ~sw ~seekable:false ~close_unix:true pid_fd in
|
let pid_fd = Fd.of_unix ~sw ~seekable:false ~close_unix:true pid_fd in
|
||||||
{ pid; pid_fd; exit_status }
|
{ pid; pid_fd; exit_status }
|
||||||
in
|
in
|
||||||
|
@ -50,7 +50,7 @@ type t = {
|
|||||||
uring: io_job Uring.t;
|
uring: io_job Uring.t;
|
||||||
mem: Uring.Region.t option;
|
mem: Uring.Region.t option;
|
||||||
io_q: (t -> unit) Queue.t; (* waiting for room on [uring] *)
|
io_q: (t -> unit) Queue.t; (* waiting for room on [uring] *)
|
||||||
mem_q : Uring.Region.chunk Suspended.t Queue.t;
|
mem_q : Uring.Region.chunk Eio.Private.Single_waiter.t Lwt_dllist.t;
|
||||||
|
|
||||||
(* The queue of runnable fibers ready to be resumed. Note: other domains can also add work items here. *)
|
(* The queue of runnable fibers ready to be resumed. Note: other domains can also add work items here. *)
|
||||||
run_q : runnable Lf_queue.t;
|
run_q : runnable Lf_queue.t;
|
||||||
@ -74,9 +74,9 @@ type t = {
|
|||||||
type _ Effect.t +=
|
type _ Effect.t +=
|
||||||
| Enter : (t -> 'a Suspended.t -> unit) -> 'a Effect.t
|
| Enter : (t -> 'a Suspended.t -> unit) -> 'a Effect.t
|
||||||
| Cancel : io_job Uring.job -> unit Effect.t
|
| Cancel : io_job Uring.job -> unit Effect.t
|
||||||
| Alloc : Uring.Region.chunk option Effect.t
|
| Get : t Effect.t
|
||||||
| Alloc_or_wait : Uring.Region.chunk Effect.t
|
|
||||||
| Free : Uring.Region.chunk -> unit Effect.t
|
let get () = Effect.perform Get
|
||||||
|
|
||||||
let wake_buffer =
|
let wake_buffer =
|
||||||
let b = Bytes.create 8 in
|
let b = Bytes.create 8 in
|
||||||
@ -247,7 +247,7 @@ let rec schedule ({run_q; sleep_q; mem_q; uring; _} as st) : [`Exit_scheduler] =
|
|||||||
) else if timeout = None && Uring.active_ops uring = 0 then (
|
) else if timeout = None && Uring.active_ops uring = 0 then (
|
||||||
(* Nothing further can happen at this point.
|
(* Nothing further can happen at this point.
|
||||||
If there are no events in progress but also still no memory available, something has gone wrong! *)
|
If there are no events in progress but also still no memory available, something has gone wrong! *)
|
||||||
assert (Queue.length mem_q = 0);
|
assert (Lwt_dllist.length mem_q = 0);
|
||||||
Lf_queue.close st.run_q; (* Just to catch bugs if something tries to enqueue later *)
|
Lf_queue.close st.run_q; (* Just to catch bugs if something tries to enqueue later *)
|
||||||
`Exit_scheduler
|
`Exit_scheduler
|
||||||
) else (
|
) else (
|
||||||
@ -339,21 +339,6 @@ and complete_rw_req st ({len; cur_off; action; _} as req) res =
|
|||||||
| _, Exactly len -> Suspended.continue action len
|
| _, Exactly len -> Suspended.continue action len
|
||||||
| n, Upto _ -> Suspended.continue action n
|
| n, Upto _ -> Suspended.continue action n
|
||||||
|
|
||||||
let alloc_buf_or_wait st k =
|
|
||||||
match st.mem with
|
|
||||||
| None -> Suspended.discontinue k (Failure "No fixed buffer available")
|
|
||||||
| Some mem ->
|
|
||||||
match Uring.Region.alloc mem with
|
|
||||||
| buf -> Suspended.continue k buf
|
|
||||||
| exception Uring.Region.No_space ->
|
|
||||||
Queue.push k st.mem_q;
|
|
||||||
schedule st
|
|
||||||
|
|
||||||
let free_buf st buf =
|
|
||||||
match Queue.take_opt st.mem_q with
|
|
||||||
| None -> Uring.Region.free buf
|
|
||||||
| Some k -> enqueue_thread st k buf
|
|
||||||
|
|
||||||
let rec enqueue_poll_add fd poll_mask st action =
|
let rec enqueue_poll_add fd poll_mask st action =
|
||||||
Trace.log "poll_add";
|
Trace.log "poll_add";
|
||||||
let retry = with_cancel_hook ~action st (fun () ->
|
let retry = with_cancel_hook ~action st (fun () ->
|
||||||
@ -411,8 +396,9 @@ let run ~extra_effects st main arg =
|
|||||||
Fiber_context.destroy fiber;
|
Fiber_context.destroy fiber;
|
||||||
Printexc.raise_with_backtrace ex (Printexc.get_raw_backtrace ())
|
Printexc.raise_with_backtrace ex (Printexc.get_raw_backtrace ())
|
||||||
);
|
);
|
||||||
effc = fun (type a) (e : a Effect.t) ->
|
effc = fun (type a) (e : a Effect.t) : ((a, _) continuation -> _) option ->
|
||||||
match e with
|
match e with
|
||||||
|
| Get -> Some (fun k -> continue k st)
|
||||||
| Enter fn -> Some (fun k ->
|
| Enter fn -> Some (fun k ->
|
||||||
match Fiber_context.get_error fiber with
|
match Fiber_context.get_error fiber with
|
||||||
| Some e -> discontinue k e
|
| Some e -> discontinue k e
|
||||||
@ -467,22 +453,6 @@ let run ~extra_effects st main arg =
|
|||||||
Eio_unix.Private.Thread_pool.submit st.thread_pool ~ctx:fiber ~enqueue fn;
|
Eio_unix.Private.Thread_pool.submit st.thread_pool ~ctx:fiber ~enqueue fn;
|
||||||
schedule st
|
schedule st
|
||||||
)
|
)
|
||||||
| Alloc -> Some (fun k ->
|
|
||||||
match st.mem with
|
|
||||||
| None -> continue k None
|
|
||||||
| Some mem ->
|
|
||||||
match Uring.Region.alloc mem with
|
|
||||||
| buf -> continue k (Some buf)
|
|
||||||
| exception Uring.Region.No_space -> continue k None
|
|
||||||
)
|
|
||||||
| Alloc_or_wait -> Some (fun k ->
|
|
||||||
let k = { Suspended.k; fiber } in
|
|
||||||
alloc_buf_or_wait st k
|
|
||||||
)
|
|
||||||
| Free buf -> Some (fun k ->
|
|
||||||
free_buf st buf;
|
|
||||||
continue k ()
|
|
||||||
)
|
|
||||||
| e -> extra_effects.effc e
|
| e -> extra_effects.effc e
|
||||||
}
|
}
|
||||||
in
|
in
|
||||||
@ -490,7 +460,7 @@ let run ~extra_effects st main arg =
|
|||||||
let `Exit_scheduler =
|
let `Exit_scheduler =
|
||||||
let new_fiber = Fiber_context.make_root () in
|
let new_fiber = Fiber_context.make_root () in
|
||||||
Domain_local_await.using
|
Domain_local_await.using
|
||||||
~prepare_for_await:Eio.Private.Dla.prepare_for_await
|
~prepare_for_await:Eio_utils.Dla.prepare_for_await
|
||||||
~while_running:(fun () ->
|
~while_running:(fun () ->
|
||||||
fork ~new_fiber (fun () ->
|
fork ~new_fiber (fun () ->
|
||||||
Switch.run_protected ~name:"eio_linux" (fun sw ->
|
Switch.run_protected ~name:"eio_linux" (fun sw ->
|
||||||
@ -551,7 +521,10 @@ let with_sched ?(fallback=no_fallback) config fn =
|
|||||||
Uring.exit uring;
|
Uring.exit uring;
|
||||||
fallback (`Msg "Linux >= 5.15 is required for io_uring support")
|
fallback (`Msg "Linux >= 5.15 is required for io_uring support")
|
||||||
) else (
|
) else (
|
||||||
statx_works := Uring.op_supported probe Uring.Op.msg_ring;
|
(* The reason for an if here is to make sure we only set it once, when
|
||||||
|
the first domain is starting. This is just to avoid a tsan warning. *)
|
||||||
|
if not !statx_works && Uring.op_supported probe Uring.Op.msg_ring then
|
||||||
|
statx_works := true;
|
||||||
match
|
match
|
||||||
let mem =
|
let mem =
|
||||||
let fixed_buf_len = block_size * n_blocks in
|
let fixed_buf_len = block_size * n_blocks in
|
||||||
@ -566,7 +539,7 @@ let with_sched ?(fallback=no_fallback) config fn =
|
|||||||
Lf_queue.push run_q IO;
|
Lf_queue.push run_q IO;
|
||||||
let sleep_q = Zzz.create () in
|
let sleep_q = Zzz.create () in
|
||||||
let io_q = Queue.create () in
|
let io_q = Queue.create () in
|
||||||
let mem_q = Queue.create () in
|
let mem_q = Lwt_dllist.create () in
|
||||||
with_eventfd @@ fun eventfd ->
|
with_eventfd @@ fun eventfd ->
|
||||||
let thread_pool = Eio_unix.Private.Thread_pool.create ~sleep_q in
|
let thread_pool = Eio_unix.Private.Thread_pool.create ~sleep_q in
|
||||||
fn { mem; uring; run_q; io_q; mem_q; eventfd; need_wakeup = Atomic.make false; sleep_q; thread_pool }
|
fn { mem; uring; run_q; io_q; mem_q; eventfd; need_wakeup = Atomic.make false; sleep_q; thread_pool }
|
||||||
|
@ -211,19 +211,52 @@ let test_signal_race () =
|
|||||||
(fun () -> Eio.Condition.await_no_mutex cond)
|
(fun () -> Eio.Condition.await_no_mutex cond)
|
||||||
(fun () -> ignore (Unix.setitimer ITIMER_REAL { it_interval = 0.; it_value = 0.001 } : Unix.interval_timer_status))
|
(fun () -> ignore (Unix.setitimer ITIMER_REAL { it_interval = 0.; it_value = 0.001 } : Unix.interval_timer_status))
|
||||||
|
|
||||||
|
let test_alloc_fixed_or_wait () =
|
||||||
|
Eio_linux.run ~n_blocks:1 @@ fun _env ->
|
||||||
|
let block = Eio_linux.Low_level.alloc_fixed_or_wait () in
|
||||||
|
(* We have to wait for the block, but get cancelled while waiting. *)
|
||||||
|
begin
|
||||||
|
try
|
||||||
|
Fiber.both
|
||||||
|
(fun () -> ignore (Eio_linux.Low_level.alloc_fixed_or_wait () : Uring.Region.chunk))
|
||||||
|
(fun () -> raise Exit);
|
||||||
|
with Exit -> ()
|
||||||
|
end;
|
||||||
|
(* We have to wait for the block, and get it when the old one is freed. *)
|
||||||
|
Fiber.both
|
||||||
|
(fun () ->
|
||||||
|
let x = Eio_linux.Low_level.alloc_fixed_or_wait () in
|
||||||
|
Eio_linux.Low_level.free_fixed x
|
||||||
|
)
|
||||||
|
(fun () ->
|
||||||
|
Eio_linux.Low_level.free_fixed block
|
||||||
|
);
|
||||||
|
(* The old block is passed to the waiting fiber, but it's cancelled. *)
|
||||||
|
let block = Eio_linux.Low_level.alloc_fixed_or_wait () in
|
||||||
|
Fiber.both
|
||||||
|
(fun () ->
|
||||||
|
Fiber.first
|
||||||
|
(fun () -> ignore (Eio_linux.Low_level.alloc_fixed_or_wait ()); assert false)
|
||||||
|
(fun () -> ())
|
||||||
|
)
|
||||||
|
(fun () -> Eio_linux.Low_level.free_fixed block);
|
||||||
|
let block = Eio_linux.Low_level.alloc_fixed_or_wait () in
|
||||||
|
Eio_linux.Low_level.free_fixed block
|
||||||
|
|
||||||
let () =
|
let () =
|
||||||
let open Alcotest in
|
let open Alcotest in
|
||||||
run "eio_linux" [
|
run "eio_linux" [
|
||||||
"io", [
|
"io", [
|
||||||
test_case "copy" `Quick test_copy;
|
test_case "copy" `Quick test_copy;
|
||||||
test_case "direct_copy" `Quick test_direct_copy;
|
test_case "direct_copy" `Quick test_direct_copy;
|
||||||
test_case "poll_add" `Quick test_poll_add;
|
test_case "poll_add" `Quick test_poll_add;
|
||||||
test_case "poll_add_busy" `Quick test_poll_add_busy;
|
test_case "poll_add_busy" `Quick test_poll_add_busy;
|
||||||
test_case "iovec" `Quick test_iovec;
|
test_case "iovec" `Quick test_iovec;
|
||||||
test_case "no_sqe" `Quick test_no_sqe;
|
test_case "no_sqe" `Quick test_no_sqe;
|
||||||
test_case "read_exact" `Quick test_read_exact;
|
test_case "read_exact" `Quick test_read_exact;
|
||||||
test_case "expose_backend" `Quick test_expose_backend;
|
test_case "expose_backend" `Quick test_expose_backend;
|
||||||
test_case "statx" `Quick test_statx;
|
test_case "statx" `Quick test_statx;
|
||||||
test_case "signal_race" `Quick test_signal_race;
|
test_case "signal_race" `Quick test_signal_race;
|
||||||
|
test_case "alloc-fixed-or-wait" `Quick test_alloc_fixed_or_wait;
|
||||||
];
|
];
|
||||||
]
|
]
|
||||||
|
@ -558,6 +558,7 @@ module Process = struct
|
|||||||
let t =
|
let t =
|
||||||
let pid =
|
let pid =
|
||||||
Fd.use_exn "errors-w" errors_w @@ fun errors_w ->
|
Fd.use_exn "errors-w" errors_w @@ fun errors_w ->
|
||||||
|
Eio.Private.Trace.with_span "spawn" @@ fun () ->
|
||||||
eio_spawn errors_w c_actions
|
eio_spawn errors_w c_actions
|
||||||
in
|
in
|
||||||
Fd.close errors_w;
|
Fd.close errors_w;
|
||||||
|
@ -379,7 +379,7 @@ let run ~extra_effects t main x =
|
|||||||
let `Exit_scheduler =
|
let `Exit_scheduler =
|
||||||
let new_fiber = Fiber_context.make_root () in
|
let new_fiber = Fiber_context.make_root () in
|
||||||
Domain_local_await.using
|
Domain_local_await.using
|
||||||
~prepare_for_await:Eio.Private.Dla.prepare_for_await
|
~prepare_for_await:Eio_utils.Dla.prepare_for_await
|
||||||
~while_running:(fun () ->
|
~while_running:(fun () ->
|
||||||
fork ~new_fiber (fun () ->
|
fork ~new_fiber (fun () ->
|
||||||
Eio_unix.Private.Thread_pool.run t.thread_pool @@ fun () ->
|
Eio_unix.Private.Thread_pool.run t.thread_pool @@ fun () ->
|
||||||
|
@ -3,8 +3,8 @@
|
|||||||
(enabled_if (= %{os_type} "Unix"))
|
(enabled_if (= %{os_type} "Unix"))
|
||||||
(deps (package eio_posix)))
|
(deps (package eio_posix)))
|
||||||
|
|
||||||
(test
|
(tests
|
||||||
(name open_beneath)
|
(names open_beneath test_await)
|
||||||
(package eio_posix)
|
(package eio_posix)
|
||||||
(build_if (= %{os_type} "Unix"))
|
(build_if (= %{os_type} "Unix"))
|
||||||
(libraries eio_posix))
|
(libraries eio_posix))
|
||||||
|
25
lib_eio_posix/test/test_await.ml
Normal file
25
lib_eio_posix/test/test_await.ml
Normal file
@ -0,0 +1,25 @@
|
|||||||
|
open Eio.Std
|
||||||
|
|
||||||
|
let () =
|
||||||
|
Eio_posix.run @@ fun _ ->
|
||||||
|
let a, b = Unix.(socketpair PF_UNIX SOCK_STREAM 0) in
|
||||||
|
(* Start awaiting readable/writable state, but cancel immediately. *)
|
||||||
|
try
|
||||||
|
Eio.Cancel.sub (fun cc ->
|
||||||
|
Fiber.all [
|
||||||
|
(fun () -> Eio_unix.await_readable a);
|
||||||
|
(fun () -> Eio_unix.await_writable b);
|
||||||
|
(fun () -> Eio.Cancel.cancel cc Exit);
|
||||||
|
];
|
||||||
|
assert false
|
||||||
|
)
|
||||||
|
with Eio.Cancel.Cancelled _ ->
|
||||||
|
(* Now wait for something else. Will fail if the old FDs are still being waited on. *)
|
||||||
|
let c, d = Unix.(socketpair PF_UNIX SOCK_STREAM 0) in
|
||||||
|
Unix.close a;
|
||||||
|
Unix.close b;
|
||||||
|
Fiber.first
|
||||||
|
(fun () -> Eio_unix.await_readable c)
|
||||||
|
(fun () -> Eio_unix.await_writable d);
|
||||||
|
Unix.close c;
|
||||||
|
Unix.close d
|
@ -6,7 +6,7 @@
|
|||||||
(foreign_stubs
|
(foreign_stubs
|
||||||
(language c)
|
(language c)
|
||||||
(include_dirs ../lib_eio/unix/include)
|
(include_dirs ../lib_eio/unix/include)
|
||||||
(names eio_windows_stubs eio_windows_cstruct_stubs))
|
(names eio_windows_stubs))
|
||||||
(c_library_flags :standard -lbcrypt -lntdll)
|
(c_library_flags :standard -lbcrypt -lntdll)
|
||||||
(libraries eio eio.unix eio.utils fmt))
|
(libraries eio eio.unix eio.utils fmt))
|
||||||
|
|
||||||
|
@ -1,149 +0,0 @@
|
|||||||
/* From mirage/ocaml-cstruct
|
|
||||||
Copyright (c) 2012 Anil Madhavapeddy <anil@recoil.org>
|
|
||||||
Copyright (c) 2012 Pierre Chambart
|
|
||||||
Copyright (c) Christiano F. Haesbaert <haesbaert@haesbaert.org>
|
|
||||||
Copyright (c) Citrix Inc
|
|
||||||
Copyright (c) David Sheets <sheets@alum.mit.edu>
|
|
||||||
Copyright (c) Drup <drupyog@zoho.com>
|
|
||||||
Copyright (c) Hannes Mehnert <hannes@mehnert.org>
|
|
||||||
Copyright (c) Jeremy Yallop <yallop@gmail.com>
|
|
||||||
Copyright (c) Mindy Preston <meetup@yomimono.org>
|
|
||||||
Copyright (c) Nicolas Ojeda Bar <n.oje.bar@gmail.com>
|
|
||||||
Copyright (c) Richard Mortier <mort@cantab.net>
|
|
||||||
Copyright (c) Rudi Grinberg <rudi.grinberg@gmail.com>
|
|
||||||
Copyright (c) Thomas Gazagnaire <thomas@gazagnaire.com>
|
|
||||||
Copyright (c) Thomas Leonard <talex5@gmail.com>
|
|
||||||
Copyright (c) Vincent Bernardoff <vb@luminar.eu.org>
|
|
||||||
Copyright (c) pqwy <david@numm.org>
|
|
||||||
|
|
||||||
Permission to use, copy, modify, and distribute this software for any
|
|
||||||
purpose with or without fee is hereby granted, provided that the above
|
|
||||||
copyright notice and this permission notice appear in all copies.
|
|
||||||
|
|
||||||
THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
|
|
||||||
WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
|
|
||||||
MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
|
|
||||||
ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
|
|
||||||
WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
|
|
||||||
ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
|
|
||||||
OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */
|
|
||||||
#include <caml/mlvalues.h>
|
|
||||||
#include <caml/memory.h>
|
|
||||||
#include <caml/custom.h>
|
|
||||||
#include <caml/callback.h>
|
|
||||||
#include <caml/alloc.h>
|
|
||||||
#include <caml/unixsupport.h>
|
|
||||||
#include <caml/bigarray.h>
|
|
||||||
#include <caml/threads.h>
|
|
||||||
#include <caml/fail.h>
|
|
||||||
|
|
||||||
#include <stdio.h>
|
|
||||||
#include <errno.h>
|
|
||||||
|
|
||||||
CAMLprim value eio_windows_cstruct_read(value val_fd, value val_c)
|
|
||||||
{
|
|
||||||
CAMLparam2(val_fd, val_c);
|
|
||||||
CAMLlocal3(val_buf, val_ofs, val_len);
|
|
||||||
uint8_t *buf;
|
|
||||||
size_t len;
|
|
||||||
ssize_t n = 0;
|
|
||||||
int win32err = 0;
|
|
||||||
SOCKET s;
|
|
||||||
HANDLE h;
|
|
||||||
DWORD numread;
|
|
||||||
int ok;
|
|
||||||
|
|
||||||
val_buf = Field(val_c, 0);
|
|
||||||
val_ofs = Field(val_c, 1);
|
|
||||||
val_len = Field(val_c, 2);
|
|
||||||
|
|
||||||
buf = (uint8_t *)Caml_ba_data_val(val_buf) + Long_val(val_ofs);
|
|
||||||
len = (size_t)Long_val(val_len);
|
|
||||||
|
|
||||||
switch (Descr_kind_val(val_fd))
|
|
||||||
{
|
|
||||||
case KIND_SOCKET:
|
|
||||||
s = Socket_val(val_fd);
|
|
||||||
|
|
||||||
caml_release_runtime_system();
|
|
||||||
n = recv(s, buf, len, 0);
|
|
||||||
win32err = WSAGetLastError();
|
|
||||||
caml_acquire_runtime_system();
|
|
||||||
|
|
||||||
if (n == SOCKET_ERROR)
|
|
||||||
{
|
|
||||||
win32_maperr(win32err);
|
|
||||||
uerror("stub_cstruct_read", Nothing);
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
case KIND_HANDLE:
|
|
||||||
h = Handle_val(val_fd);
|
|
||||||
caml_release_runtime_system();
|
|
||||||
ok = ReadFile(h, buf, len, &numread, NULL);
|
|
||||||
win32err = GetLastError();
|
|
||||||
n = numread;
|
|
||||||
caml_acquire_runtime_system();
|
|
||||||
|
|
||||||
if (!ok)
|
|
||||||
{
|
|
||||||
win32_maperr(win32err);
|
|
||||||
uerror("stub_cstruct_read", Nothing);
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
default:
|
|
||||||
caml_failwith("unknown Descr_kind_val");
|
|
||||||
}
|
|
||||||
|
|
||||||
CAMLreturn(Val_int(n));
|
|
||||||
}
|
|
||||||
|
|
||||||
CAMLprim value eio_windows_cstruct_write(value val_fd, value val_c)
|
|
||||||
{
|
|
||||||
CAMLparam2(val_fd, val_c);
|
|
||||||
CAMLlocal3(val_buf, val_ofs, val_len);
|
|
||||||
val_buf = Field(val_c, 0);
|
|
||||||
val_ofs = Field(val_c, 1);
|
|
||||||
val_len = Field(val_c, 2);
|
|
||||||
void *buf = (char *)Caml_ba_data_val(val_buf) + Long_val(val_ofs);
|
|
||||||
size_t len = Long_val(val_len);
|
|
||||||
ssize_t n = 0;
|
|
||||||
|
|
||||||
int win32err = 0;
|
|
||||||
switch (Descr_kind_val(val_fd))
|
|
||||||
{
|
|
||||||
case KIND_SOCKET:
|
|
||||||
SOCKET s = Socket_val(val_fd);
|
|
||||||
|
|
||||||
caml_release_runtime_system();
|
|
||||||
n = send(s, buf, len, 0);
|
|
||||||
win32err = WSAGetLastError();
|
|
||||||
caml_acquire_runtime_system();
|
|
||||||
|
|
||||||
if (n == SOCKET_ERROR)
|
|
||||||
{
|
|
||||||
win32_maperr(win32err);
|
|
||||||
unix_error(errno, "stub_cstruct_write", Nothing);
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
case KIND_HANDLE:
|
|
||||||
HANDLE h = Handle_val(val_fd);
|
|
||||||
DWORD numwritten;
|
|
||||||
caml_release_runtime_system();
|
|
||||||
int ok = WriteFile(h, buf, len, &numwritten, NULL);
|
|
||||||
win32err = GetLastError();
|
|
||||||
|
|
||||||
n = numwritten;
|
|
||||||
caml_acquire_runtime_system();
|
|
||||||
|
|
||||||
if (!ok)
|
|
||||||
{
|
|
||||||
win32_maperr(win32err);
|
|
||||||
uerror("stub_cstruct_write", Nothing);
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
default:
|
|
||||||
caml_failwith("unknown Descr_kind_val");
|
|
||||||
}
|
|
||||||
|
|
||||||
CAMLreturn(Val_int(n));
|
|
||||||
}
|
|
@ -237,7 +237,7 @@ CAMLprim value caml_eio_windows_unlinkat(value v_dirfd, value v_pathname, value
|
|||||||
|
|
||||||
if (!NT_SUCCESS(r)) {
|
if (!NT_SUCCESS(r)) {
|
||||||
caml_win32_maperr(RtlNtStatusToDosError(r));
|
caml_win32_maperr(RtlNtStatusToDosError(r));
|
||||||
uerror("openat", Nothing);
|
uerror("openat", v_pathname);
|
||||||
}
|
}
|
||||||
|
|
||||||
// Now close the file to delete it
|
// Now close the file to delete it
|
||||||
|
@ -20,7 +20,7 @@ let wrap code name arg =
|
|||||||
| ENOENT -> Eio.Fs.err (Not_found e)
|
| ENOENT -> Eio.Fs.err (Not_found e)
|
||||||
| EXDEV | EACCES | EPERM -> Eio.Fs.err (Permission_denied e)
|
| EXDEV | EACCES | EPERM -> Eio.Fs.err (Permission_denied e)
|
||||||
| ECONNREFUSED -> Eio.Net.err (Connection_failure (Refused e))
|
| ECONNREFUSED -> Eio.Net.err (Connection_failure (Refused e))
|
||||||
| ECONNRESET | EPIPE -> Eio.Net.err (Connection_reset e)
|
| ECONNRESET | EPIPE | ECONNABORTED -> Eio.Net.err (Connection_reset e)
|
||||||
| _ -> unclassified_error e
|
| _ -> unclassified_error e
|
||||||
|
|
||||||
let run fn x =
|
let run fn x =
|
||||||
|
@ -82,7 +82,7 @@ end = struct
|
|||||||
let dir = resolve t dir in
|
let dir = resolve t dir in
|
||||||
Switch.run @@ fun sw ->
|
Switch.run @@ fun sw ->
|
||||||
let open Low_level in
|
let open Low_level in
|
||||||
let dirfd = Low_level.openat ~sw ~nofollow:true dir Flags.Open.(generic_read + synchronise) Flags.Disposition.(open_if) Flags.Create.(directory) in
|
let dirfd = Err.run (Low_level.openat ~sw ~nofollow:true dir Flags.Open.(generic_read + synchronise) Flags.Disposition.(open_if)) Flags.Create.(directory) in
|
||||||
fn (Some dirfd) leaf
|
fn (Some dirfd) leaf
|
||||||
)
|
)
|
||||||
) else fn None path
|
) else fn None path
|
||||||
|
@ -39,17 +39,25 @@ let rec do_nonblocking ty fn fd =
|
|||||||
do_nonblocking ty fn fd
|
do_nonblocking ty fn fd
|
||||||
|
|
||||||
let read fd buf start len =
|
let read fd buf start len =
|
||||||
|
await_readable fd;
|
||||||
Fd.use_exn "read" fd @@ fun fd ->
|
Fd.use_exn "read" fd @@ fun fd ->
|
||||||
do_nonblocking Read (fun fd -> Unix.read fd buf start len) fd
|
do_nonblocking Read (fun fd -> Unix.read fd buf start len) fd
|
||||||
|
|
||||||
let read_cstruct fd buf =
|
let read_cstruct fd (buf:Cstruct.t) =
|
||||||
|
await_readable fd;
|
||||||
Fd.use_exn "read_cstruct" fd @@ fun fd ->
|
Fd.use_exn "read_cstruct" fd @@ fun fd ->
|
||||||
do_nonblocking Read (fun fd -> Unix_cstruct.read fd buf) fd
|
do_nonblocking Read (fun fd -> Unix.read_bigarray fd buf.buffer buf.off buf.len) fd
|
||||||
|
|
||||||
let write fd buf start len =
|
let write fd buf start len =
|
||||||
|
await_writable fd;
|
||||||
Fd.use_exn "write" fd @@ fun fd ->
|
Fd.use_exn "write" fd @@ fun fd ->
|
||||||
do_nonblocking Write (fun fd -> Unix.write fd buf start len) fd
|
do_nonblocking Write (fun fd -> Unix.write fd buf start len) fd
|
||||||
|
|
||||||
|
let write_cstruct fd (buf:Cstruct.t) =
|
||||||
|
await_writable fd;
|
||||||
|
Fd.use_exn "write_cstruct" fd @@ fun fd ->
|
||||||
|
do_nonblocking Write (fun fd -> Unix.write_bigarray fd buf.buffer buf.off buf.len) fd
|
||||||
|
|
||||||
let sleep_until time =
|
let sleep_until time =
|
||||||
Sched.enter @@ fun t k ->
|
Sched.enter @@ fun t k ->
|
||||||
Sched.await_timeout t k time
|
Sched.await_timeout t k time
|
||||||
@ -148,8 +156,11 @@ let readv fd bufs =
|
|||||||
do_nonblocking Read (fun fd -> eio_readv fd bufs) fd
|
do_nonblocking Read (fun fd -> eio_readv fd bufs) fd
|
||||||
|
|
||||||
let writev fd bufs =
|
let writev fd bufs =
|
||||||
Fd.use_exn "writev" fd @@ fun fd ->
|
let rec loop buf = if Cstruct.length buf > 0 then begin
|
||||||
do_nonblocking Write (fun fd -> Unix_cstruct.writev fd bufs) fd
|
let n = write_cstruct fd buf in
|
||||||
|
loop @@ Cstruct.shift buf n
|
||||||
|
end in
|
||||||
|
List.iter loop bufs
|
||||||
|
|
||||||
let preadv ~file_offset fd bufs =
|
let preadv ~file_offset fd bufs =
|
||||||
Fd.use_exn "preadv" fd @@ fun fd ->
|
Fd.use_exn "preadv" fd @@ fun fd ->
|
||||||
|
@ -22,6 +22,7 @@ val sleep_until : Mtime.t -> unit
|
|||||||
val read : fd -> bytes -> int -> int -> int
|
val read : fd -> bytes -> int -> int -> int
|
||||||
val read_cstruct : fd -> Cstruct.t -> int
|
val read_cstruct : fd -> Cstruct.t -> int
|
||||||
val write : fd -> bytes -> int -> int -> int
|
val write : fd -> bytes -> int -> int -> int
|
||||||
|
val write_cstruct : fd -> Cstruct.t -> int
|
||||||
|
|
||||||
val socket : sw:Switch.t -> Unix.socket_domain -> Unix.socket_type -> int -> fd
|
val socket : sw:Switch.t -> Unix.socket_domain -> Unix.socket_type -> int -> fd
|
||||||
val connect : fd -> Unix.sockaddr -> unit
|
val connect : fd -> Unix.sockaddr -> unit
|
||||||
|
@ -83,24 +83,23 @@ let datagram_handler = Eio_unix.Pi.datagram_handler (module Datagram_socket)
|
|||||||
let datagram_socket fd =
|
let datagram_socket fd =
|
||||||
Eio.Resource.T (fd, datagram_handler)
|
Eio.Resource.T (fd, datagram_handler)
|
||||||
|
|
||||||
(* https://www.iana.org/assignments/protocol-numbers/protocol-numbers.xhtml *)
|
|
||||||
let getaddrinfo ~service node =
|
let getaddrinfo ~service node =
|
||||||
let to_eio_sockaddr_t {Unix.ai_family; ai_addr; ai_socktype; ai_protocol; _ } =
|
(* OCaml's [Unix.getaddrinfo] on Windows doesn't set [ai_protocol] to
|
||||||
match ai_family, ai_socktype, ai_addr with
|
anything useful, so you can't tell which addresses are TCP and which are
|
||||||
| (Unix.PF_INET | PF_INET6),
|
UDP. So, do two separate queries. *)
|
||||||
(Unix.SOCK_STREAM | SOCK_DGRAM),
|
let get ty k =
|
||||||
Unix.ADDR_INET (inet_addr,port) -> (
|
Unix.getaddrinfo node service [AI_SOCKTYPE ty]
|
||||||
match ai_protocol with
|
|> List.filter_map (function
|
||||||
| 6 -> Some (`Tcp (Eio_unix.Net.Ipaddr.of_unix inet_addr, port))
|
| {Unix.ai_addr = ADDR_INET (host, port); _} ->
|
||||||
| 17 -> Some (`Udp (Eio_unix.Net.Ipaddr.of_unix inet_addr, port))
|
Some (k (Eio_unix.Net.Ipaddr.of_unix host, port))
|
||||||
| _ -> None)
|
| _ -> None
|
||||||
| _ -> None
|
)
|
||||||
in
|
in
|
||||||
Err.run (Eio_unix.run_in_systhread ~label:"getaddrinfo") @@ fun () ->
|
Err.run (Eio_unix.run_in_systhread ~label:"getaddrinfo") @@ fun () ->
|
||||||
let rec aux () =
|
let rec aux () =
|
||||||
try
|
try
|
||||||
Unix.getaddrinfo node service []
|
get SOCK_STREAM (fun x -> `Tcp x) @
|
||||||
|> List.filter_map to_eio_sockaddr_t
|
get SOCK_DGRAM (fun x -> `Udp x)
|
||||||
with Unix.Unix_error (EINTR, _, _) -> aux ()
|
with Unix.Unix_error (EINTR, _, _) -> aux ()
|
||||||
in
|
in
|
||||||
aux ()
|
aux ()
|
||||||
|
@ -271,6 +271,8 @@ let await_readable t (k : unit Suspended.t) fd =
|
|||||||
if was_empty then update t waiters fd;
|
if was_empty then update t waiters fd;
|
||||||
Fiber_context.set_cancel_fn k.fiber (fun ex ->
|
Fiber_context.set_cancel_fn k.fiber (fun ex ->
|
||||||
Lwt_dllist.remove node;
|
Lwt_dllist.remove node;
|
||||||
|
if Lwt_dllist.is_empty waiters.read then
|
||||||
|
update t waiters fd;
|
||||||
t.active_ops <- t.active_ops - 1;
|
t.active_ops <- t.active_ops - 1;
|
||||||
enqueue_failed_thread t k ex
|
enqueue_failed_thread t k ex
|
||||||
);
|
);
|
||||||
@ -287,6 +289,8 @@ let await_writable t (k : unit Suspended.t) fd =
|
|||||||
if was_empty then update t waiters fd;
|
if was_empty then update t waiters fd;
|
||||||
Fiber_context.set_cancel_fn k.fiber (fun ex ->
|
Fiber_context.set_cancel_fn k.fiber (fun ex ->
|
||||||
Lwt_dllist.remove node;
|
Lwt_dllist.remove node;
|
||||||
|
if Lwt_dllist.is_empty waiters.write then
|
||||||
|
update t waiters fd;
|
||||||
t.active_ops <- t.active_ops - 1;
|
t.active_ops <- t.active_ops - 1;
|
||||||
enqueue_failed_thread t k ex
|
enqueue_failed_thread t k ex
|
||||||
);
|
);
|
||||||
@ -370,7 +374,7 @@ let run ~extra_effects t main x =
|
|||||||
let `Exit_scheduler =
|
let `Exit_scheduler =
|
||||||
let new_fiber = Fiber_context.make_root () in
|
let new_fiber = Fiber_context.make_root () in
|
||||||
Domain_local_await.using
|
Domain_local_await.using
|
||||||
~prepare_for_await:Eio.Private.Dla.prepare_for_await
|
~prepare_for_await:Eio_utils.Dla.prepare_for_await
|
||||||
~while_running:(fun () ->
|
~while_running:(fun () ->
|
||||||
fork ~new_fiber (fun () ->
|
fork ~new_fiber (fun () ->
|
||||||
Eio_unix.Private.Thread_pool.run t.thread_pool @@ fun () ->
|
Eio_unix.Private.Thread_pool.run t.thread_pool @@ fun () ->
|
||||||
|
@ -1,3 +1,5 @@
|
|||||||
|
open Eio.Std
|
||||||
|
|
||||||
module Timeout = struct
|
module Timeout = struct
|
||||||
let test clock () =
|
let test clock () =
|
||||||
let t0 = Unix.gettimeofday () in
|
let t0 = Unix.gettimeofday () in
|
||||||
@ -48,6 +50,35 @@ module Dla = struct
|
|||||||
]
|
]
|
||||||
end
|
end
|
||||||
|
|
||||||
|
module Await_fd = struct
|
||||||
|
let test_cancel () =
|
||||||
|
let a, b = Unix.(socketpair PF_UNIX SOCK_STREAM 0) in
|
||||||
|
(* Start awaiting readable/writable state, but cancel immediately. *)
|
||||||
|
try
|
||||||
|
Eio.Cancel.sub (fun cc ->
|
||||||
|
Fiber.all [
|
||||||
|
(fun () -> Eio_unix.await_readable a);
|
||||||
|
(fun () -> Eio_unix.await_writable b);
|
||||||
|
(fun () -> Eio.Cancel.cancel cc Exit);
|
||||||
|
];
|
||||||
|
assert false
|
||||||
|
)
|
||||||
|
with Eio.Cancel.Cancelled _ ->
|
||||||
|
(* Now wait for something else. Will fail if the old FDs are still being waited on. *)
|
||||||
|
let c, d = Unix.(socketpair PF_UNIX SOCK_STREAM 0) in
|
||||||
|
Unix.close a;
|
||||||
|
Unix.close b;
|
||||||
|
Fiber.first
|
||||||
|
(fun () -> Eio_unix.await_readable c)
|
||||||
|
(fun () -> Eio_unix.await_writable d);
|
||||||
|
Unix.close c;
|
||||||
|
Unix.close d
|
||||||
|
|
||||||
|
let tests = [
|
||||||
|
"cancel", `Quick, test_cancel;
|
||||||
|
]
|
||||||
|
end
|
||||||
|
|
||||||
|
|
||||||
let () =
|
let () =
|
||||||
Eio_windows.run @@ fun env ->
|
Eio_windows.run @@ fun env ->
|
||||||
@ -56,5 +87,6 @@ let () =
|
|||||||
"fs", Test_fs.tests env;
|
"fs", Test_fs.tests env;
|
||||||
"timeout", Timeout.tests env;
|
"timeout", Timeout.tests env;
|
||||||
"random", Random.tests env;
|
"random", Random.tests env;
|
||||||
"dla", Dla.tests
|
"dla", Dla.tests;
|
||||||
]
|
"await", Await_fd.tests;
|
||||||
|
]
|
||||||
|
@ -158,6 +158,9 @@ let test_symlink env () =
|
|||||||
Unix.mkdir "another" 0o700;
|
Unix.mkdir "another" 0o700;
|
||||||
print_endline @@ Unix.realpath "to-subdir" |}
|
print_endline @@ Unix.realpath "to-subdir" |}
|
||||||
*)
|
*)
|
||||||
|
if not (Unix.has_symlink ()) then
|
||||||
|
Printf.printf "Skipping test_symlink on systems that don't support symlinks.\n"
|
||||||
|
else
|
||||||
let cwd = Eio.Stdenv.cwd env in
|
let cwd = Eio.Stdenv.cwd env in
|
||||||
try_mkdir (cwd / "sandbox");
|
try_mkdir (cwd / "sandbox");
|
||||||
Unix.symlink ~to_dir:true ".." "sandbox\\to-root";
|
Unix.symlink ~to_dir:true ".." "sandbox\\to-root";
|
||||||
@ -277,4 +280,5 @@ let tests env = [
|
|||||||
"unlink", `Quick, test_unlink env;
|
"unlink", `Quick, test_unlink env;
|
||||||
"failing-unlink", `Quick, try_failing_unlink env;
|
"failing-unlink", `Quick, try_failing_unlink env;
|
||||||
"rmdir", `Quick, test_remove_dir env;
|
"rmdir", `Quick, test_remove_dir env;
|
||||||
|
"mkdirs", `Quick, test_mkdirs env;
|
||||||
]
|
]
|
26
tests/fs.md
26
tests/fs.md
@ -985,3 +985,29 @@ Exception: Failure "Simulated error".
|
|||||||
+seek from end: 9
|
+seek from end: 9
|
||||||
- : unit = ()
|
- : unit = ()
|
||||||
```
|
```
|
||||||
|
|
||||||
|
# Extending paths
|
||||||
|
|
||||||
|
```ocaml
|
||||||
|
# run @@ fun env ->
|
||||||
|
let base = fst env#cwd in
|
||||||
|
List.iter (fun (a, b) -> traceln "%S / %S = %S" a b (snd ((base, a) / b))) [
|
||||||
|
"foo", "bar";
|
||||||
|
"foo/", "bar";
|
||||||
|
"foo", "/bar";
|
||||||
|
"foo", "";
|
||||||
|
"foo/", "";
|
||||||
|
"", "";
|
||||||
|
"", "bar";
|
||||||
|
"/", "";
|
||||||
|
]
|
||||||
|
+"foo" / "bar" = "foo/bar"
|
||||||
|
+"foo/" / "bar" = "foo/bar"
|
||||||
|
+"foo" / "/bar" = "/bar"
|
||||||
|
+"foo" / "" = "foo/"
|
||||||
|
+"foo/" / "" = "foo/"
|
||||||
|
+"" / "" = ""
|
||||||
|
+"" / "bar" = "bar"
|
||||||
|
+"/" / "" = "/"
|
||||||
|
- : unit = ()
|
||||||
|
```
|
||||||
|
@ -620,7 +620,9 @@ Exception: Eio.Io Fs Not_found _,
|
|||||||
```ocaml
|
```ocaml
|
||||||
# Eio_main.run @@ fun env ->
|
# Eio_main.run @@ fun env ->
|
||||||
let sockaddr = `Tcp (Eio.Net.Ipaddr.V4.loopback, 80) in
|
let sockaddr = `Tcp (Eio.Net.Ipaddr.V4.loopback, 80) in
|
||||||
Eio.Net.getnameinfo env#net sockaddr;;
|
let (host, service) = Eio.Net.getnameinfo env#net sockaddr in
|
||||||
|
let service = if service = "www" then "http" else service in (* OpenBSD *)
|
||||||
|
(host, service)
|
||||||
- : string * string = ("localhost", "http")
|
- : string * string = ("localhost", "http")
|
||||||
```
|
```
|
||||||
|
|
||||||
|
@ -145,24 +145,24 @@ If a command fails, we get shown the arguments (quoted if necessary):
|
|||||||
|
|
||||||
```ocaml
|
```ocaml
|
||||||
# run @@ fun mgr env ->
|
# run @@ fun mgr env ->
|
||||||
Process.run mgr ["bash"; "-c"; "exit 3"; ""; "foo"; "\"bar\""];;
|
Process.run mgr ["sh"; "-c"; "exit 3"; ""; "foo"; "\"bar\""];;
|
||||||
Exception:
|
Exception:
|
||||||
Eio.Io Process Child_error Exited (code 3),
|
Eio.Io Process Child_error Exited (code 3),
|
||||||
running command: bash -c "exit 3" "" foo "\"bar\""
|
running command: sh -c "exit 3" "" foo "\"bar\""
|
||||||
```
|
```
|
||||||
|
|
||||||
Exit code success can be determined by is_success (Process.run):
|
Exit code success can be determined by is_success (Process.run):
|
||||||
|
|
||||||
```ocaml
|
```ocaml
|
||||||
# run @@ fun mgr env ->
|
# run @@ fun mgr env ->
|
||||||
Process.run ~is_success:(Int.equal 3) mgr ["bash"; "-c"; "exit 3"];;
|
Process.run ~is_success:(Int.equal 3) mgr ["sh"; "-c"; "exit 3"];;
|
||||||
- : unit = ()
|
- : unit = ()
|
||||||
|
|
||||||
# run @@ fun mgr env ->
|
# run @@ fun mgr env ->
|
||||||
Process.run ~is_success:(Int.equal 3) mgr ["bash"; "-c"; "exit 0"];;
|
Process.run ~is_success:(Int.equal 3) mgr ["sh"; "-c"; "exit 0"];;
|
||||||
Exception:
|
Exception:
|
||||||
Eio.Io Process Child_error Exited (code 0),
|
Eio.Io Process Child_error Exited (code 0),
|
||||||
running command: bash -c "exit 0"
|
running command: sh -c "exit 0"
|
||||||
```
|
```
|
||||||
|
|
||||||
Exit code success can be determined by is_success (Process.parse_out):
|
Exit code success can be determined by is_success (Process.parse_out):
|
||||||
|
Loading…
x
Reference in New Issue
Block a user