Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add support for unknown integer types. #652

Open
wants to merge 1 commit into
base: master
Choose a base branch
from
Open

Add support for unknown integer types. #652

wants to merge 1 commit into from

Conversation

yallop
Copy link
Owner

@yallop yallop commented Jul 15, 2020

Aims and background

This PR adds support for using integer types of unknown properties (size, alignment requirements, signedness).

For example, POSIX specifies that off_t is a signed integer type, but does not specify its size. And it specifies that dev_t is an integer type, but does not specify its size or signedness. This PR makes it possible to bind and use both types nonetheless.

Similarly, the C standard allows implementations to choose the properties of enum types. Implementations sometimes also include extensions (such as GCC's -fshort-enums) that allow users to vary those properties. That implementation freedom can make it difficult to use enums from ctypes (cf. #650). This PR makes it easier to bind and use such types in ctypes code.

Design

This PR adds two new functions, signed and unsigned, to the Ctypes.TYPE signature:

val signed  : string -> (module signed)
val unsigned : string -> (module unsigned)

Users can apply these functions in type-binding functions to bind integer types of unknown properties:

module Types(C: Ctypes.TYPE) =
struct
  open C
  
  let dev_t = signed "dev_t"
  let flags = unsigned "enum flags"
end

and unpack the bindings to build modules with information about those types:

module Dev_t = (val dev_t)
module Flags = (val flags)

The signatures for Dev_t and Flags include all the standard integer operations (from Signed.S or Unsigned.S) as well as a typ value that makes it possible to use the new types to create values, bind functions, etc.

module type signed = sig include Signed.S val t : t typ end
module type unsigned = sig include Unsigned.S val t : t typ end

Limitations

Since the type binding interface currently requires that functors such as Types above are applicative, it is not possible to unpack Dev_t and Flags inside the functor.

@yallop yallop mentioned this pull request Jul 15, 2020
@fdopen
Copy link
Contributor

fdopen commented Jul 15, 2020

It's similar to: https://fdopen.github.io/ppx_cstubs/opaque/#integers-of-unknown-size-and-signedness
But I've added an explicit function for integers of unknown signedness, instead of implicit conversions from a signed type to an unsigned interface.
I also use custom modules for int8/int16. Otherwise max_int is wrong and the overflow semantic might be surprising.

@yallop yallop closed this by deleting the head repository Sep 28, 2022
@yallop yallop reopened this Sep 28, 2022
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants