{"id":21420754,"url":"https://github.com/zelang-dev/uv_coroutine","last_synced_at":"2025-07-14T06:32:31.461Z","repository":{"id":167674902,"uuid":"643299240","full_name":"zelang-dev/c-coroutine","owner":"zelang-dev","description":"A simple C coroutine library, with multithreading and more, the Go and C++20 style way. ","archived":false,"fork":false,"pushed_at":"2023-12-24T02:13:44.000Z","size":10813,"stargazers_count":33,"open_issues_count":0,"forks_count":1,"subscribers_count":3,"default_branch":"main","last_synced_at":"2023-12-24T22:04:00.947Z","etag":null,"topics":["concurrent-futures","concurrent-programming","cooperative-multitasking","coroutine","event-driven","mutlithreading","parallel-programming"],"latest_commit_sha":null,"homepage":"https://zelang-dev.github.io/c-coroutine/","language":"C","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"mit","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/zelang-dev.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":"LICENSE.md","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null}},"created_at":"2023-05-20T18:07:38.000Z","updated_at":"2024-04-14T23:44:08.160Z","dependencies_parsed_at":"2023-10-15T16:19:31.593Z","dependency_job_id":"e8d9043e-063d-4c86-9e0f-d8e2992b8654","html_url":"https://github.com/zelang-dev/c-coroutine","commit_stats":null,"previous_names":["symplely/c-coroutine","zelang-dev/c-coroutine"],"tags_count":0,"template":null,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/zelang-dev%2Fc-coroutine","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/zelang-dev%2Fc-coroutine/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/zelang-dev%2Fc-coroutine/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/zelang-dev%2Fc-coroutine/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/zelang-dev","download_url":"https://codeload.github.com/zelang-dev/c-coroutine/tar.gz/refs/heads/main","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":225959804,"owners_count":17551618,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["concurrent-futures","concurrent-programming","cooperative-multitasking","coroutine","event-driven","mutlithreading","parallel-programming"],"created_at":"2024-11-22T20:21:40.197Z","updated_at":"2025-07-14T06:32:31.445Z","avatar_url":"https://github.com/zelang-dev.png","language":"C","funding_links":[],"categories":[],"sub_categories":[],"readme":"# uv_coroutine\n\n[![windows \u0026 linux \u0026 macOS](https://github.com/zelang-dev/uv_coroutine/actions/workflows/ci.yml/badge.svg)](https://github.com/zelang-dev/uv_coroutine/actions/workflows/ci.yml)[![macOS](https://github.com/zelang-dev/uv_coroutine/actions/workflows/ci_macos.yml/badge.svg)](https://github.com/zelang-dev/uv_coroutine/actions/workflows/ci_macos.yml)[![armv7, aarch64, ppc64le](https://github.com/zelang-dev/uv_coroutine/actions/workflows/ci_qemu_others.yml/badge.svg)](https://github.com/zelang-dev/uv_coroutine/actions/workflows/ci_qemu_others.yml)[![riscv64 \u0026 s390x by ucontext  .](https://github.com/zelang-dev/uv_coroutine/actions/workflows/ci_qemu.yml/badge.svg)](https://github.com/zelang-dev/uv_coroutine/actions/workflows/ci_qemu.yml)\n\n## Table of Contents\n\n* [Introduction](#introduction)\n* [Synopsis](#synopsis)\n* [Usage](#usage)\n* [Installation](#installation)\n* [Contributing](#contributing)\n* [License](#license)\n\n## Introduction\n\nThis library provides **ease of use** *convenience* wrappers for **[libuv](http://docs.libuv.org)** combined with the power of **[c-raii](https://zelang-dev.github.io/c-raii)**, a **high level memory management** library similar to other languages, among other features. Like **[coroutine](https://github.com/zelang-dev/c-raii/blob/main/include/coro.h)** support, the otherwise **callback** needed, is now automatically back to the caller with *results*.\n\n* All functions requiring *allocation* and *passing* **pointers**, now returns them instead, if needed.\n* The general naming convention is to drop **~~uv_~~** prefix and require only *necessary* arguments/options.\n* This integration also requires the use of **`uv_main(int argc, char **argv)`** as the *startup* entry routine:\n\n**libuv** example from \u003chttps://github.com/libuv/libuv/tree/master/docs/code/\u003e\n\n\u003ctable\u003e\n\u003ctr\u003e\n\u003cth\u003ehelloworld.c\u003c/th\u003e\n\u003cth\u003ehelloworld/main.c\u003c/th\u003e\n\u003c/tr\u003e\n\u003ctr\u003e\n\u003ctd\u003e\n\n```c\n#include \"uv_coro.h\"\n\nint uv_main(int argc, char **argv) {\n    printf(\"Now quitting.\\n\");\n    yield();\n\n    return coro_err_code();\n}\n```\n\n\u003c/td\u003e\n\u003ctd\u003e\n\n```c\n#include \u003cstdio.h\u003e\n#include \u003cstdlib.h\u003e\n#include \u003cuv.h\u003e\n\nint main() {\n    uv_loop_t *loop = malloc(sizeof(uv_loop_t));\n    uv_loop_init(loop);\n\n    printf(\"Now quitting.\\n\");\n    uv_run(loop, UV_RUN_DEFAULT);\n\n    uv_loop_close(loop);\n    free(loop);\n    return 0;\n}\n```\n\n\u003c/td\u003e\n\u003c/tr\u003e\n\u003c/table\u003e\n\n**This general means there will be a dramatic reduction of lines of code repeated, repeatedly.**\n\n*Libuv guides/examples:*\n\n* [Reading/Writing files](https://docs.libuv.org/en/v1.x/guide/filesystem.html#reading-writing-files) as in [uvcat/main.c](https://github.com/libuv/libuv/blob/master/docs/code/uvcat/main.c) - 62 line *script*.\n* [Buffers and Streams](https://docs.libuv.org/en/v1.x/guide/filesystem.html#buffers-and-streams) as in [uvtee/main.c](https://github.com/libuv/libuv/blob/master/docs/code/uvtee/main.c) - 79 line *script*.\n* [Spawning child processes](https://docs.libuv.org/en/v1.x/guide/processes.html#spawning-child-processes) as in [spawn/main.c](https://github.com/libuv/libuv/blob/master/docs/code/spawn/main.c) - 36 line *script*.\n* [Networking/TCP](https://docs.libuv.org/en/v1.x/guide/networking.html#tcp) as in [tcp-echo-server/main.c](https://github.com/libuv/libuv/blob/master/docs/code/tcp-echo-server/main.c) - 87 line *script*.\n\n*Reduced to:*\n\u003ctable\u003e\n\u003ctr\u003e\n\u003cth\u003euvcat.c - 13 lines\u003c/th\u003e\n\u003cth\u003euvtee.c - 20 lines\u003c/th\u003e\n\u003c/tr\u003e\n\u003ctr\u003e\n\u003ctd\u003e\n\n```c\n#include \"uv_coro.h\"\n\nint uv_main(int argc, char **argv) {\n    uv_file fd = fs_open(argv[1], O_RDONLY, 0);\n    if (fd \u003e 0) {\n        string text = fs_read(fd, -1);\n        fs_write(STDOUT_FILENO, text, -1);\n\n        return fs_close(fd);\n    }\n\n    return fd;\n}\n```\n\n\u003c/td\u003e\n\u003ctd\u003e\n\n```c\n#include \"uv_coro.h\"\n\nint uv_main(int argc, char **argv) {\n    string text = nullptr;\n    uv_file fd = fs_open(argv[1], O_CREAT | O_RDWR, 0644);\n    if (fd \u003e 0) {\n        pipe_file_t *file_pipe = pipe_file(fd, false);\n        pipe_out_t *stdout_pipe = pipe_stdout(false);\n        pipe_in_t *stdin_pipe = pipe_stdin(false);\n        while (text = stream_read(stdin_pipe-\u003ereader)) {\n            if (stream_write(stdout_pipe-\u003ewriter, text)\n                || stream_write(file_pipe-\u003ehandle, text))\n                break;\n        }\n\n        return fs_close(fd);\n    }\n\n    return fd;\n}\n```\n\n\u003c/td\u003e\n\u003c/tr\u003e\n\u003c/table\u003e\n\n\u003ctable\u003e\n\u003ctr\u003e\n\u003cth\u003espawn.c - 13 lines\u003c/th\u003e\n\u003c/tr\u003e\n\u003ctr\u003e\n\u003ctd\u003e\n\n```c\n#include \"uv_coro.h\"\n\nvoid _on_exit(int64_t exit_status, int term_signal) {\n    fprintf(stderr, \"\\nProcess exited with status %\" PRId64 \", signal %d\\n\", exit_status, term_signal);\n}\n\nint uv_main(int argc, char **argv) {\n    spawn_t child = spawn(\"mkdir\", \"test-dir\", nullptr);\n    if (!spawn_atexit(child, _on_exit))\n        fprintf(stderr, \"\\nLaunched process with ID %d\\n\", spawn_pid(child));\n\n    return coro_err_code();\n}\n```\n\n\u003c/td\u003e\n\u003c/tr\u003e\n\u003c/table\u003e\n\n\u003ctable\u003e\n\u003ctr\u003e\n\u003cth\u003etcp-echo-server.c - 27 lines\u003c/th\u003e\n\u003c/tr\u003e\n\u003ctr\u003e\n\u003ctd\u003e\n\n```c\n#include \"uv_coro.h\"\n\n#define DEFAULT_PORT 7000\n#define DEFAULT_BACKLOG 128\n\nvoid new_connection(uv_stream_t *socket) {\n    string data = stream_read(socket);\n    stream_write(socket, data);\n}\n\nint uv_main(int argc, char **argv) {\n    uv_stream_t *client, *server;\n    char addr[UV_MAXHOSTNAMESIZE] = nil;\n\n    if (snprintf(addr, sizeof(addr), \"0.0.0.0:%d\", DEFAULT_PORT)) {\n        server = stream_bind(addr, 0);\n        while (server) {\n            if (is_empty(client = stream_listen(server, DEFAULT_BACKLOG))) {\n                fprintf(stderr, \"Listen error %s\\n\", uv_strerror(coro_err_code()));\n                break;\n            }\n\n            stream_handler(new_connection, client);\n        }\n    }\n\n    return coro_err_code();\n}\n```\n\n\u003c/td\u003e\n\u003c/tr\u003e\n\u003c/table\u003e\n\nSee `branches` for previous setup, `main` is an complete makeover of previous implementation approaches.\n\nSimilar approach has been made for ***C++20***, an implementation in [uvco](https://github.com/dermesser/uvco).\nThe *[tests](https://github.com/dermesser/uvco/tree/master/test)* presented there currently being reimplemented for *C89* here, this project will be considered stable when *completed*. And another approach in [libasync](https://github.com/btrask/libasync) mixing [libco](https://github.com/higan-emu/libco) with **libuv**. Both approaches are **Linux** only.\n\n## Synopsis\n\n```c\n\n```\n\n## Usage\n\n### See [examples](https://github.com/zelang-dev/uv_coroutine/tree/main/examples) and [tests](https://github.com/zelang-dev/uv_coroutine/tree/main/tests) folder\n\n## Installation\n\nThe build system uses **cmake**, that produces **static** libraries by default.\n\n**Linux**\n\n```shell\nmkdir build\ncd build\ncmake .. -D CMAKE_BUILD_TYPE=Debug/Release -D BUILD_EXAMPLES=ON -D BUILD_TESTS=ON # use to build files in tests/examples folder\ncmake --build .\n```\n\n**Windows**\n\n```shell\nmkdir build\ncd build\ncmake .. -D BUILD_EXAMPLES=ON -D BUILD_TESTS=ON # use to build files in tests/examples folder\ncmake --build . --config Debug/Release\n```\n\n## Contributing\n\nContributions are encouraged and welcome; I am always happy to get feedback or pull requests on Github :) Create [Github Issues](https://github.com/zelang-dev/uv_coroutine/issues) for bugs and new features and comment on the ones you are interested in.\n\n## License\n\nThe MIT License (MIT). Please see [License File](LICENSE.md) for more information.\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fzelang-dev%2Fuv_coroutine","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fzelang-dev%2Fuv_coroutine","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fzelang-dev%2Fuv_coroutine/lists"}