141 lines
2.8 KiB
Odin
141 lines
2.8 KiB
Odin
package cimport
|
|
|
|
import "../target"
|
|
import "core:mem"
|
|
|
|
Type_Id :: distinct u32
|
|
INVALID_TYPE :: Type_Id(0xffff_ffff)
|
|
|
|
Type_Kind :: enum u8 {
|
|
Invalid,
|
|
Void,
|
|
C_Char,
|
|
C_Schar,
|
|
C_Uchar,
|
|
C_Short,
|
|
C_Ushort,
|
|
C_Int,
|
|
C_Uint,
|
|
C_Long,
|
|
C_Ulong,
|
|
C_Longlong,
|
|
C_Ulonglong,
|
|
C_Float,
|
|
C_Double,
|
|
C_Longdouble,
|
|
Pointer,
|
|
Record,
|
|
}
|
|
|
|
Type :: struct {
|
|
kind: Type_Kind,
|
|
child: Type_Id,
|
|
record: u32,
|
|
mutable: bool,
|
|
}
|
|
|
|
Record :: struct {
|
|
name: string,
|
|
identity: string,
|
|
}
|
|
|
|
Alias :: struct {
|
|
name: string,
|
|
type: Type_Id,
|
|
reason: string,
|
|
}
|
|
|
|
Function :: struct {
|
|
name: string,
|
|
params: []Type_Id,
|
|
result: Type_Id,
|
|
reason: string,
|
|
}
|
|
|
|
Unsupported :: struct {
|
|
name: string,
|
|
reason: string,
|
|
}
|
|
|
|
Result :: struct {
|
|
types: [dynamic]Type,
|
|
records: [dynamic]Record,
|
|
aliases: [dynamic]Alias,
|
|
functions: [dynamic]Function,
|
|
unsupported: [dynamic]Unsupported,
|
|
error_message: string,
|
|
infrastructure: bool,
|
|
available: bool,
|
|
allocator: mem.Allocator,
|
|
}
|
|
|
|
init_result :: proc(allocator := context.allocator) -> Result {
|
|
result: Result
|
|
result.allocator = allocator
|
|
result.types.allocator = allocator
|
|
result.records.allocator = allocator
|
|
result.aliases.allocator = allocator
|
|
result.functions.allocator = allocator
|
|
result.unsupported.allocator = allocator
|
|
return result
|
|
}
|
|
|
|
destroy_result :: proc(result: ^Result) {
|
|
for record in result.records {
|
|
delete(record.name, result.allocator)
|
|
delete(record.identity, result.allocator)
|
|
}
|
|
for alias in result.aliases {
|
|
delete(alias.name, result.allocator)
|
|
delete(alias.reason, result.allocator)
|
|
}
|
|
for function in result.functions {
|
|
delete(function.name, result.allocator)
|
|
delete(function.params, result.allocator)
|
|
delete(function.reason, result.allocator)
|
|
}
|
|
for item in result.unsupported {
|
|
delete(item.name, result.allocator)
|
|
delete(item.reason, result.allocator)
|
|
}
|
|
delete(result.error_message, result.allocator)
|
|
delete(result.types)
|
|
delete(result.records)
|
|
delete(result.aliases)
|
|
delete(result.functions)
|
|
delete(result.unsupported)
|
|
}
|
|
|
|
Request :: struct {
|
|
path: string,
|
|
include_paths: []string,
|
|
defines: []string,
|
|
target: target.Target,
|
|
}
|
|
|
|
Backend_Proc :: proc(user_data: rawptr, request: Request, allocator: mem.Allocator) -> Result
|
|
|
|
Backend :: struct {
|
|
import_header: Backend_Proc,
|
|
user_data: rawptr,
|
|
}
|
|
|
|
Options :: struct {
|
|
include_paths: []string,
|
|
defines: []string,
|
|
backend: Backend,
|
|
}
|
|
|
|
import_header :: proc(options: Options, path: string, selected := target.DEFAULT, allocator := context.allocator) -> Result {
|
|
request := Request{
|
|
path=path,
|
|
include_paths=options.include_paths,
|
|
defines=options.defines,
|
|
target=selected,
|
|
}
|
|
if options.backend.import_header != nil {
|
|
return options.backend.import_header(options.backend.user_data, request, allocator)
|
|
}
|
|
return import_with_libclang(nil, request, allocator)
|
|
}
|