commit f7c67698c69c695c77743d089e0523622d723e44 Author: Philippe PITTOLI Date: Wed Jun 19 20:00:25 2024 +0200 IPCd: first commit. Basic switch. diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..43c3d91 --- /dev/null +++ b/.gitignore @@ -0,0 +1,6 @@ +/docs/ +/lib/ +/bin/ +/.shards/ +*.dwarf +shard.lock diff --git a/README.md b/README.md new file mode 100644 index 0000000..bbaed3f --- /dev/null +++ b/README.md @@ -0,0 +1,27 @@ +# ipcd + +TODO: Write a description here + +## Installation + +TODO: Write installation instructions here + +## Usage + +TODO: Write usage instructions here + +## Development + +TODO: Write development instructions here + +## Contributing + +1. Fork it () +2. Create your feature branch (`git checkout -b my-new-feature`) +3. Commit your changes (`git commit -am 'Add some feature'`) +4. Push to the branch (`git push origin my-new-feature`) +5. Create a new Pull Request + +## Contributors + +- [Philippe PITTOLI](https://github.com/your-github-user) - creator and maintainer diff --git a/shard.yml b/shard.yml new file mode 100644 index 0000000..44841ce --- /dev/null +++ b/shard.yml @@ -0,0 +1,17 @@ +name: ipcd +version: 0.1.0 + +authors: + - Philippe PITTOLI + +targets: + ipcd: + main: src/ipcd.cr + +dependencies: + ipc: + git: https://git.baguette.netlib.re/Baguette/ipc.cr + +crystal: '>= 1.12.2' + +license: ISC diff --git a/src/ipcd.cr b/src/ipcd.cr new file mode 100644 index 0000000..8114eb7 --- /dev/null +++ b/src/ipcd.cr @@ -0,0 +1,83 @@ +require "ipc" + +# TODO: Write documentation for `IPCd` +module IPCd + VERSION = "0.1.0" + + def self.start + ipcd = IPC.new() + ipcd.service_init "hello" + ipcd.timer 10_000 + ipcd.loop do |event| + begin + case event.type + when LibIPC::EventType::Timer + puts "Timer." + + when LibIPC::EventType::Connection + fd = ipcd.connect "pong" + ipcd.add_switch event.newfd, fd + input = -> fn_input( LibC::Int, LibC::Char*, LibC::UInt64T*) + output = -> fn_output(LibC::Int, LibC::Char*, LibC::UInt64T ) + ipcd.switch_callbacks event.newfd, input, output + puts "New connection (#{event.newfd}) now automatically switched to 'pong' (#{fd})!" + + when LibIPC::EventType::Disconnection + puts "Disconnection from #{event.fd}." + + when LibIPC::EventType::MessageTx + puts "Message sent to #{event.fd}." + + when LibIPC::EventType::MessageRx + puts "Message received from #{event.fd}." + + when LibIPC::EventType::SwitchRx + puts "Switch message received from #{event.fd}." + + when LibIPC::EventType::SwitchTx + puts "Switch message sent to #{event.fd}." + + when LibIPC::EventType::Error + puts "And error occured on fd #{event.fd}." + + else + puts "Unhandled IPC event: #{event.class}." + if event.responds_to?(:fd) + puts "closing #{event.fd}" + ipcd.close event.fd + end + end + + rescue exception + puts "exception: #{typeof(exception)} - #{exception.message}" + end + end + end +end + +def fn_input(fd : LibC::Int, buffer : LibC::Char*, buflen : LibC::UInt64T*) : LibC::Char + puts "switch input: #{fd}" + io = IO::FileDescriptor.new fd, close_on_finalize: false + slice = Bytes.new buffer, buflen.value + len = io.read slice + buflen.value = len.to_u64 + return 2_u8 if (len == 0) + 0_u8 +rescue e + puts "fn_input exception! #{e}" + 1_u8 +end + +def fn_output(fd : LibC::Int, buffer : LibC::Char*, buflen : LibC::UInt64T) : LibC::Char + puts "switch output: #{fd}" + slice = Bytes.new buffer, buflen + io = IO::FileDescriptor.new fd, close_on_finalize: false + io.write slice + io.flush + 0_u8 +rescue e + puts "fn_output exception! #{e}" + 1_u8 +end + +IPCd.start