{"id":27991243,"url":"https://github.com/pinselimo/cstructs-in-haskell","last_synced_at":"2025-10-26T13:34:41.022Z","repository":{"id":51064513,"uuid":"280127347","full_name":"pinselimo/cstructs-in-haskell","owner":"pinselimo","description":"C-Struct Types for Haskell","archived":false,"fork":false,"pushed_at":"2022-09-30T07:47:36.000Z","size":112,"stargazers_count":3,"open_issues_count":0,"forks_count":0,"subscribers_count":2,"default_branch":"master","last_synced_at":"2025-05-08T16:56:51.213Z","etag":null,"topics":["c","ffi","hackage","haskell","haskell-ffi","haskell-library","struct"],"latest_commit_sha":null,"homepage":"","language":"Haskell","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/pinselimo.png","metadata":{"files":{"readme":"README.md","changelog":"CHANGELOG.md","contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null}},"created_at":"2020-07-16T10:42:22.000Z","updated_at":"2023-04-29T12:47:05.000Z","dependencies_parsed_at":"2022-09-04T03:40:52.300Z","dependency_job_id":null,"html_url":"https://github.com/pinselimo/cstructs-in-haskell","commit_stats":null,"previous_names":[],"tags_count":0,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/pinselimo%2Fcstructs-in-haskell","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/pinselimo%2Fcstructs-in-haskell/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/pinselimo%2Fcstructs-in-haskell/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/pinselimo%2Fcstructs-in-haskell/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/pinselimo","download_url":"https://codeload.github.com/pinselimo/cstructs-in-haskell/tar.gz/refs/heads/master","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":253112073,"owners_count":21856070,"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":["c","ffi","hackage","haskell","haskell-ffi","haskell-library","struct"],"created_at":"2025-05-08T16:56:57.899Z","updated_at":"2025-10-26T13:34:36.003Z","avatar_url":"https://github.com/pinselimo.png","language":"Haskell","funding_links":[],"categories":[],"sub_categories":[],"readme":"# C-Structs in Haskell [![Haskell CI](https://github.com/pinselimo/cstructs-in-haskell/actions/workflows/haskell.yml/badge.svg)](https://github.com/pinselimo/cstructs-in-haskell/actions/workflows/haskell.yml) \u003c!-- [![Hackage CI](https://matrix.hackage.haskell.org/api/v2/packages/C-structs/badge)](https://matrix.hackage.haskell.org/package/C-structs) --\u003e [![Hackage Version](https://img.shields.io/hackage/v/C-structs.svg?label=Hackage)](http://hackage.haskell.org/package/C-structs) [![Dependencies of latest version on Hackage](https://img.shields.io/hackage-deps/v/C-structs.svg)](https://hackage.haskell.org/package/C-structs)\n\nC-structs lets you create dynamically typed and correctly padded C structs in Haskell.\nThese can be used for FFI calls, imports and exports.\nThis package is part of the development efforts for the Python library [```Pythas```](https://github.com/pinselimo/Pythas/).\nPythas provides an interface to import Haskell modules.\n\nNote: As of GHC 9.2 structs cannot be passed by value, [only by reference](https://wiki.haskell.org/Foreign_Function_Interface#Foreign_types).\n\n## Usage\n\nYou can use these types as a classic ```hackage``` package.\nThe library has no other dependencies than some of the ```Foreign.*``` modules contained in ```base```.\n\n### Basics\n\n~~~haskell\nλ\u003e import Foreign.C.Structs\nλ\u003e s = Struct2 1 2 :: Struct2 Int Int\n~~~\n\ncan be interpreted as an equivalent to:\n\n~~~C\nstruct Struct2 {\n    int s21st;\n    int s22nd;\n};\n\nstruct Struct2 s;\ns.s21st = 1;\ns.s22nd = 2;\n~~~\n\nor with Python's ```ctypes```:\n\n~~~python\n\u003e\u003e\u003e from ctypes import Structure, c_int\n\u003e\u003e\u003e class Struct2( Structure ):\n...     _fields_ = [(\"s21st\", c_int), (\"s22nd\", c_int)]\n...\n\u003e\u003e\u003e s = Struct2(1,2)\n~~~\n\nOn memory all of these examples should have the exact same representation.\nA pointer to either ```s``` can then be exchanged with the other and used in a ```foreign``` call.\n\n### FFI usage\n\nThe following shows an example of a foreign import of a ```struct Struct2``` as defined above:\n\n~~~C\nstruct Struct2 *foo (void) {\n    struct Struct2 *val;\n    val = malloc (sizeof (struct Struct2));\n    val-\u003es21st = 42;\n    val-\u003es22nd = 63;\n    return val;\n}\n~~~\n\ncan be imported in a Haskell module as follows:\n\n~~~haskell\n{-# LANGUAGE ForeignFunctionInterface #-}\n\nimport Foreign.Ptr (Ptr)\nimport Foreign.Storable (peek)\nimport Foreign.Marshal.Alloc (free)\nimport Foreign.C.Types (CInt)\nimport Foreign.C.Structs (Struct2)\n\nforeign import ccall \"foo\" foo :: Ptr (Struct2 CInt CInt)\n\nmain = do\n    putStrLn \"Reading values from C..\"\n    s \u003c- peek foo\n    free foo\n    putStrLn \"Received:\"\n    putStrLn $ show s\n~~~\n\nFor a more elaborated usage examples checkout [```Pythas```](https://github.com/pinselimo/Pythas) in conjunction with [```Pythas-Types```](https://github.com/pinselimo/Pythas-Types).\nIt uses ```Foreign.C.Structs``` to declare its storage functions for ```Haskell``` tuples. In addition, its Array and Linked List instances are based on this library.\n\n### More fields\n\nCurrently ```C-structs``` exports types featuring up to six fields. If you require more, you can easily create them using Template Haskell and the ```structT``` function:\n\n~~~haskell\nstructT 8\n~~~\n\nwill create:\n\n~~~haskell\ndata Struct8 = Struct8\n    { s81st :: a\n    , s82nd :: b\n    , s83rd :: c\n    , s84th :: d\n    , s85th :: e\n    ...\n    } deriving (Show, Eq)\n\ninstance Storable Struct8 ...\n~~~\n\n### Accessors\n\nThe naming scheme of the accessor functions follows the names of the ordinal numbers. This can be inconvenient in a Template Haskell context. For these situations ```Foreign.C.Structs``` exposes the ```acs``` function:\n\n~~~haskell\n$(acs 8 2)\n~~~\n\nThis expression will be spliced into a function taking a ```Struct8``` and extracting its second field.\n\n## Testing\n\nIdentity properties are tested with QuickCheck to ensure that peek and poke are reversible.\nThe result of ```sizeOf``` is dependent on the order of types. Its correctness can only be tested with HUnit.\nThe ```alignment``` function is trivial and only tested implicitly through ```sizeOf```.\n\nImports from C are tested in ```CTest.hs``` and together with the identity tests form the guarantee that also exports to C are consistent.\nUntil Travis CI became unusable for FOSS projects all tests were performed for all available GHC/CABAL/Stack versions through the [Stack CI script](https://docs.haskellstack.org/en/stable/travis_ci/) on both Linux and OSX to ensure maximum compatibility. Now only the latest GHC versions are checked on Linux, macOS and Windows using cabal through GitHub Actions. Compatibility with older versions of GHC should however be kept.\n\n## License\n\nThis part of Pythas is licensed under the ```MIT``` License. Please be aware that the full ```Pythas``` package is under ```LGPLv3```. Refer to the accompanying LICENSE or COPYING files for details.\n\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fpinselimo%2Fcstructs-in-haskell","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fpinselimo%2Fcstructs-in-haskell","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fpinselimo%2Fcstructs-in-haskell/lists"}