Double pointer support
This commit is contained in:
parent
28e2d7bb87
commit
454403b9fe
7 changed files with 111 additions and 32 deletions
|
|
@ -23,6 +23,7 @@ proc saveNodeData(node: TSNode, nimState: NimState): bool =
|
||||||
pname = node.getPxName(1)
|
pname = node.getPxName(1)
|
||||||
ppname = node.getPxName(2)
|
ppname = node.getPxName(2)
|
||||||
pppname = node.getPxName(3)
|
pppname = node.getPxName(3)
|
||||||
|
ppppname = node.getPxName(4)
|
||||||
|
|
||||||
if node.tsNodePrevNamedSibling().tsNodeIsNull():
|
if node.tsNodePrevNamedSibling().tsNodeIsNull():
|
||||||
if pname == "pointer_declarator":
|
if pname == "pointer_declarator":
|
||||||
|
|
@ -30,9 +31,15 @@ proc saveNodeData(node: TSNode, nimState: NimState): bool =
|
||||||
nimState.data.add(("pointer_declarator", ""))
|
nimState.data.add(("pointer_declarator", ""))
|
||||||
elif ppname == "array_declarator":
|
elif ppname == "array_declarator":
|
||||||
nimState.data.add(("array_pointer_declarator", ""))
|
nimState.data.add(("array_pointer_declarator", ""))
|
||||||
|
|
||||||
|
# Double pointer
|
||||||
|
if ppname == "pointer_declarator":
|
||||||
|
nimState.data.add(("pointer_declarator", ""))
|
||||||
elif pname in ["function_declarator", "array_declarator"]:
|
elif pname in ["function_declarator", "array_declarator"]:
|
||||||
if ppname == "pointer_declarator":
|
if ppname == "pointer_declarator":
|
||||||
nimState.data.add(("pointer_declarator", ""))
|
nimState.data.add(("pointer_declarator", ""))
|
||||||
|
if pppname == "pointer_declarator":
|
||||||
|
nimState.data.add(("pointer_declarator", ""))
|
||||||
|
|
||||||
nimState.data.add((name, val))
|
nimState.data.add((name, val))
|
||||||
|
|
||||||
|
|
@ -41,6 +48,8 @@ proc saveNodeData(node: TSNode, nimState: NimState): bool =
|
||||||
ppname == "function_declarator":
|
ppname == "function_declarator":
|
||||||
if pppname == "pointer_declarator":
|
if pppname == "pointer_declarator":
|
||||||
nimState.data.insert(("pointer_declarator", ""), nimState.data.len-1)
|
nimState.data.insert(("pointer_declarator", ""), nimState.data.len-1)
|
||||||
|
if ppppname == "pointer_declarator":
|
||||||
|
nimState.data.insert(("pointer_declarator", ""), nimState.data.len-1)
|
||||||
nimState.data.add(("function_declarator", ""))
|
nimState.data.add(("function_declarator", ""))
|
||||||
|
|
||||||
elif name in gExpressions:
|
elif name in gExpressions:
|
||||||
|
|
|
||||||
|
|
@ -24,7 +24,7 @@ using
|
||||||
var
|
var
|
||||||
when while
|
when while
|
||||||
xor
|
xor
|
||||||
yield""".split(Whitespace).toSet()
|
yield""".split(Whitespace).toHashSet()
|
||||||
|
|
||||||
const gTypeMap = {
|
const gTypeMap = {
|
||||||
# char
|
# char
|
||||||
|
|
@ -151,8 +151,12 @@ proc getPtrType*(str: string): string =
|
||||||
result = case str:
|
result = case str:
|
||||||
of "ptr cchar":
|
of "ptr cchar":
|
||||||
"cstring"
|
"cstring"
|
||||||
|
of "ptr ptr cchar":
|
||||||
|
"ptr cstring"
|
||||||
of "ptr object":
|
of "ptr object":
|
||||||
"pointer"
|
"pointer"
|
||||||
|
of "ptr ptr object":
|
||||||
|
"ptr pointer"
|
||||||
else:
|
else:
|
||||||
str
|
str
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -16,14 +16,14 @@ const
|
||||||
"primitive_type",
|
"primitive_type",
|
||||||
"sized_type_specifier",
|
"sized_type_specifier",
|
||||||
"type_identifier"
|
"type_identifier"
|
||||||
].toSet()
|
].toHashSet()
|
||||||
|
|
||||||
gExpressions {.used.} = @[
|
gExpressions {.used.} = @[
|
||||||
"parenthesized_expression",
|
"parenthesized_expression",
|
||||||
"bitwise_expression",
|
"bitwise_expression",
|
||||||
"shift_expression",
|
"shift_expression",
|
||||||
"math_expression"
|
"math_expression"
|
||||||
].toSet()
|
].toHashSet()
|
||||||
|
|
||||||
gEnumVals {.used.} = @[
|
gEnumVals {.used.} = @[
|
||||||
"identifier",
|
"identifier",
|
||||||
|
|
|
||||||
|
|
@ -50,6 +50,9 @@ proc initGrammar(): Grammar =
|
||||||
{typeGrammar}
|
{typeGrammar}
|
||||||
(identifier|type_identifier?)
|
(identifier|type_identifier?)
|
||||||
(pointer_declarator?
|
(pointer_declarator?
|
||||||
|
(pointer_declarator!
|
||||||
|
(identifier|type_identifier)
|
||||||
|
)
|
||||||
(identifier|type_identifier)
|
(identifier|type_identifier)
|
||||||
)
|
)
|
||||||
(abstract_pointer_declarator?)
|
(abstract_pointer_declarator?)
|
||||||
|
|
@ -61,6 +64,9 @@ proc initGrammar(): Grammar =
|
||||||
(function_declarator*
|
(function_declarator*
|
||||||
(identifier|type_identifier!)
|
(identifier|type_identifier!)
|
||||||
(pointer_declarator
|
(pointer_declarator
|
||||||
|
(pointer_declarator!
|
||||||
|
(type_identifier)
|
||||||
|
)
|
||||||
(type_identifier)
|
(type_identifier)
|
||||||
)
|
)
|
||||||
{paramListGrammar}
|
{paramListGrammar}
|
||||||
|
|
@ -70,6 +76,9 @@ proc initGrammar(): Grammar =
|
||||||
arrGrammar = &"""
|
arrGrammar = &"""
|
||||||
(array_declarator!
|
(array_declarator!
|
||||||
(pointer_declarator!
|
(pointer_declarator!
|
||||||
|
(pointer_declarator!
|
||||||
|
(type_identifier)
|
||||||
|
)
|
||||||
(type_identifier)
|
(type_identifier)
|
||||||
)
|
)
|
||||||
(type_identifier)
|
(type_identifier)
|
||||||
|
|
@ -80,11 +89,10 @@ proc initGrammar(): Grammar =
|
||||||
template funcParamCommon(fname, pname, ptyp, pptr, pout, count, i: untyped): untyped =
|
template funcParamCommon(fname, pname, ptyp, pptr, pout, count, i: untyped): untyped =
|
||||||
ptyp = nimState.data[i].val.getIdentifier(nskType, fname)
|
ptyp = nimState.data[i].val.getIdentifier(nskType, fname)
|
||||||
|
|
||||||
if i+1 < nimState.data.len and nimState.data[i+1].name == "pointer_declarator":
|
pptr = ""
|
||||||
pptr = "ptr "
|
while i+1 < nimState.data.len and nimState.data[i+1].name == "pointer_declarator":
|
||||||
|
pptr &= "ptr "
|
||||||
i += 1
|
i += 1
|
||||||
else:
|
|
||||||
pptr = ""
|
|
||||||
|
|
||||||
if i+1 < nimState.data.len and nimState.data[i+1].name == "identifier":
|
if i+1 < nimState.data.len and nimState.data[i+1].name == "identifier":
|
||||||
pname = nimState.data[i+1].val.getIdentifier(nskParam, fname)
|
pname = nimState.data[i+1].val.getIdentifier(nskParam, fname)
|
||||||
|
|
@ -94,8 +102,8 @@ proc initGrammar(): Grammar =
|
||||||
count += 1
|
count += 1
|
||||||
i += 1
|
i += 1
|
||||||
|
|
||||||
if pptr == "ptr " or ptyp != "object":
|
if pptr.len != 0 or ptyp != "object":
|
||||||
pout &= &"{pname}: {getPtrType(pptr&ptyp)},"
|
pout &= &"{pname}: {getPtrType(pptr&ptyp)}, "
|
||||||
|
|
||||||
# typedef int X
|
# typedef int X
|
||||||
# typedef X Y
|
# typedef X Y
|
||||||
|
|
@ -107,6 +115,11 @@ proc initGrammar(): Grammar =
|
||||||
(type_identifier!)
|
(type_identifier!)
|
||||||
{arrGrammar}
|
{arrGrammar}
|
||||||
(pointer_declarator!
|
(pointer_declarator!
|
||||||
|
(pointer_declarator!
|
||||||
|
(type_identifier!)
|
||||||
|
{arrGrammar}
|
||||||
|
{funcGrammar}
|
||||||
|
)
|
||||||
(type_identifier!)
|
(type_identifier!)
|
||||||
{arrGrammar}
|
{arrGrammar}
|
||||||
{funcGrammar}
|
{funcGrammar}
|
||||||
|
|
@ -123,13 +136,13 @@ proc initGrammar(): Grammar =
|
||||||
aptr = ""
|
aptr = ""
|
||||||
|
|
||||||
i += 1
|
i += 1
|
||||||
if i < nimState.data.len:
|
while i < nimState.data.len and "pointer" in nimState.data[i].name:
|
||||||
case nimState.data[i].name:
|
case nimState.data[i].name:
|
||||||
of "pointer_declarator":
|
of "pointer_declarator":
|
||||||
tptr = "ptr "
|
tptr &= "ptr "
|
||||||
i += 1
|
i += 1
|
||||||
of "array_pointer_declarator":
|
of "array_pointer_declarator":
|
||||||
aptr = "ptr "
|
aptr &= "ptr "
|
||||||
i += 1
|
i += 1
|
||||||
|
|
||||||
if i < nimState.data.len:
|
if i < nimState.data.len:
|
||||||
|
|
@ -149,10 +162,10 @@ proc initGrammar(): Grammar =
|
||||||
|
|
||||||
funcParamCommon(fname, pname, ptyp, pptr, pout, count, i)
|
funcParamCommon(fname, pname, ptyp, pptr, pout, count, i)
|
||||||
|
|
||||||
if pout.len != 0 and pout[^1] == ',':
|
if pout.len != 0 and pout[^2 .. ^1] == ", ":
|
||||||
pout = pout[0 .. ^2]
|
pout = pout[0 .. ^3]
|
||||||
|
|
||||||
if tptr == "ptr " or typ != "object":
|
if tptr.len != 0 or typ != "object":
|
||||||
nimState.typeStr &= &"\n {name}* = proc({pout}): {getPtrType(tptr&typ)} {{.nimcall.}}"
|
nimState.typeStr &= &"\n {name}* = proc({pout}): {getPtrType(tptr&typ)} {{.nimcall.}}"
|
||||||
else:
|
else:
|
||||||
nimState.typeStr &= &"\n {name}* = proc({pout}) {{.nimcall.}}"
|
nimState.typeStr &= &"\n {name}* = proc({pout}) {{.nimcall.}}"
|
||||||
|
|
@ -242,13 +255,14 @@ proc initGrammar(): Grammar =
|
||||||
ftyp = nimState.data[i].val.getType()
|
ftyp = nimState.data[i].val.getType()
|
||||||
i += 1
|
i += 1
|
||||||
|
|
||||||
case nimState.data[i].name:
|
while i < nimState.data.len-fend and "pointer" in nimState.data[i].name:
|
||||||
of "pointer_declarator":
|
case nimState.data[i].name:
|
||||||
fptr = "ptr "
|
of "pointer_declarator":
|
||||||
i += 1
|
fptr &= "ptr "
|
||||||
of "array_pointer_declarator":
|
i += 1
|
||||||
aptr = "ptr "
|
of "array_pointer_declarator":
|
||||||
i += 1
|
aptr &= "ptr "
|
||||||
|
i += 1
|
||||||
|
|
||||||
fname = nimState.data[i].val.getIdentifier(nskField, nname)
|
fname = nimState.data[i].val.getIdentifier(nskField, nname)
|
||||||
|
|
||||||
|
|
@ -273,9 +287,9 @@ proc initGrammar(): Grammar =
|
||||||
|
|
||||||
funcParamCommon(fname, pname, ptyp, pptr, pout, count, i)
|
funcParamCommon(fname, pname, ptyp, pptr, pout, count, i)
|
||||||
|
|
||||||
if pout.len != 0 and pout[^1] == ',':
|
if pout.len != 0 and pout[^2 .. ^1] == ", ":
|
||||||
pout = pout[0 .. ^2]
|
pout = pout[0 .. ^3]
|
||||||
if fptr == "ptr " or ftyp != "object":
|
if fptr.len != 0 or ftyp != "object":
|
||||||
nimState.typeStr &= &"\n {fname}*: proc({pout}): {getPtrType(fptr&ftyp)} {{.nimcall.}}"
|
nimState.typeStr &= &"\n {fname}*: proc({pout}): {getPtrType(fptr&ftyp)} {{.nimcall.}}"
|
||||||
else:
|
else:
|
||||||
nimState.typeStr &= &"\n {fname}*: proc({pout}) {{.nimcall.}}"
|
nimState.typeStr &= &"\n {fname}*: proc({pout}) {{.nimcall.}}"
|
||||||
|
|
@ -297,12 +311,18 @@ proc initGrammar(): Grammar =
|
||||||
(array_declarator!
|
(array_declarator!
|
||||||
(field_identifier!)
|
(field_identifier!)
|
||||||
(pointer_declarator
|
(pointer_declarator
|
||||||
|
(pointer_declarator!
|
||||||
|
(field_identifier)
|
||||||
|
)
|
||||||
(field_identifier)
|
(field_identifier)
|
||||||
)
|
)
|
||||||
(^$1+)
|
(^$1+)
|
||||||
)
|
)
|
||||||
(function_declarator+
|
(function_declarator+
|
||||||
(pointer_declarator
|
(pointer_declarator
|
||||||
|
(pointer_declarator!
|
||||||
|
(field_identifier)
|
||||||
|
)
|
||||||
(field_identifier)
|
(field_identifier)
|
||||||
)
|
)
|
||||||
{paramListGrammar}
|
{paramListGrammar}
|
||||||
|
|
@ -314,6 +334,9 @@ proc initGrammar(): Grammar =
|
||||||
(field_declaration+
|
(field_declaration+
|
||||||
{typeGrammar}
|
{typeGrammar}
|
||||||
(pointer_declarator!
|
(pointer_declarator!
|
||||||
|
(pointer_declarator!
|
||||||
|
{fieldGrammar}
|
||||||
|
)
|
||||||
{fieldGrammar}
|
{fieldGrammar}
|
||||||
)
|
)
|
||||||
{fieldGrammar}
|
{fieldGrammar}
|
||||||
|
|
@ -341,6 +364,9 @@ proc initGrammar(): Grammar =
|
||||||
)
|
)
|
||||||
(type_identifier!)
|
(type_identifier!)
|
||||||
(pointer_declarator
|
(pointer_declarator
|
||||||
|
(pointer_declarator!
|
||||||
|
(type_identifier)
|
||||||
|
)
|
||||||
(type_identifier)
|
(type_identifier)
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
|
|
@ -433,6 +459,9 @@ proc initGrammar(): Grammar =
|
||||||
{result[^1].grammar}
|
{result[^1].grammar}
|
||||||
(type_identifier!)
|
(type_identifier!)
|
||||||
(pointer_declarator
|
(pointer_declarator
|
||||||
|
(pointer_declarator!
|
||||||
|
(type_identifier)
|
||||||
|
)
|
||||||
(type_identifier)
|
(type_identifier)
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
|
|
@ -459,6 +488,9 @@ proc initGrammar(): Grammar =
|
||||||
(storage_class_specifier?)
|
(storage_class_specifier?)
|
||||||
{typeGrammar}
|
{typeGrammar}
|
||||||
(pointer_declarator!
|
(pointer_declarator!
|
||||||
|
(pointer_declarator!
|
||||||
|
{funcGrammar}
|
||||||
|
)
|
||||||
{funcGrammar}
|
{funcGrammar}
|
||||||
)
|
)
|
||||||
{funcGrammar}
|
{funcGrammar}
|
||||||
|
|
@ -474,11 +506,10 @@ proc initGrammar(): Grammar =
|
||||||
i += 1
|
i += 1
|
||||||
continue
|
continue
|
||||||
|
|
||||||
if nimState.data[i].name == "pointer_declarator":
|
fptr = ""
|
||||||
fptr = "ptr "
|
while i < nimState.data.len and nimState.data[i].name == "pointer_declarator":
|
||||||
|
fptr &= "ptr "
|
||||||
i += 1
|
i += 1
|
||||||
else:
|
|
||||||
fptr = ""
|
|
||||||
|
|
||||||
var
|
var
|
||||||
fname = nimState.data[i].val
|
fname = nimState.data[i].val
|
||||||
|
|
@ -493,12 +524,12 @@ proc initGrammar(): Grammar =
|
||||||
|
|
||||||
funcParamCommon(fnname, pname, ptyp, pptr, pout, count, i)
|
funcParamCommon(fnname, pname, ptyp, pptr, pout, count, i)
|
||||||
|
|
||||||
if pout.len != 0 and pout[^1] == ',':
|
if pout.len != 0 and pout[^2 .. ^1] == ", ":
|
||||||
pout = pout[0 .. ^2]
|
pout = pout[0 .. ^3]
|
||||||
|
|
||||||
if fnname.nBl and nimState.identifiers.addNewIdentifer(fnname):
|
if fnname.nBl and nimState.identifiers.addNewIdentifer(fnname):
|
||||||
let ftyp = nimState.data[0].val.getIdentifier(nskType, fnname)
|
let ftyp = nimState.data[0].val.getIdentifier(nskType, fnname)
|
||||||
if fptr == "ptr " or ftyp != "object":
|
if fptr.len != 0 or ftyp != "object":
|
||||||
nimState.procStr &= &"\nproc {fnname}*({pout}): {getPtrType(fptr&ftyp)} {{.{genImportC(fname, fnname)}, header: {nimState.currentHeader}.}}"
|
nimState.procStr &= &"\nproc {fnname}*({pout}): {getPtrType(fptr&ftyp)} {{.{genImportC(fname, fnname)}, header: {nimState.currentHeader}.}}"
|
||||||
else:
|
else:
|
||||||
nimState.procStr &= &"\nproc {fnname}*({pout}) {{.{genImportC(fname, fnname)}, header: {nimState.currentHeader}.}}"
|
nimState.procStr &= &"\nproc {fnname}*({pout}) {{.{genImportC(fname, fnname)}, header: {nimState.currentHeader}.}}"
|
||||||
|
|
|
||||||
|
|
@ -60,6 +60,10 @@ void *test_call9() {
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void **test_call10(int **param1) {
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
void multiline1(void) {}
|
void multiline1(void) {}
|
||||||
|
|
||||||
void *multiline2(void) {
|
void *multiline2(void) {
|
||||||
|
|
|
||||||
|
|
@ -108,6 +108,7 @@ unsigned char test_call_param6(UNION2 param1);
|
||||||
int test_call_param7(union UNION1 param1);
|
int test_call_param7(union UNION1 param1);
|
||||||
float test_call_param8(int *param1);
|
float test_call_param8(int *param1);
|
||||||
void *test_call9();
|
void *test_call9();
|
||||||
|
void **test_call10(int **param1);
|
||||||
|
|
||||||
// Issue #58
|
// Issue #58
|
||||||
void
|
void
|
||||||
|
|
@ -131,6 +132,20 @@ UNION3 test_call_etype_ptr3();
|
||||||
|
|
||||||
typedef struct _Kernel { char name; } *Kernel;
|
typedef struct _Kernel { char name; } *Kernel;
|
||||||
|
|
||||||
|
// Double pointers
|
||||||
|
typedef void **DVOIDPTR;
|
||||||
|
typedef int **DINTPTR;
|
||||||
|
|
||||||
|
struct dstruct {
|
||||||
|
int **field1;
|
||||||
|
};
|
||||||
|
|
||||||
|
typedef struct dstruct2 {
|
||||||
|
char **field1;
|
||||||
|
float **field2;
|
||||||
|
void **(*tcv)(int **param1);
|
||||||
|
} DSTRUCT2;
|
||||||
|
|
||||||
#ifdef __cplusplus
|
#ifdef __cplusplus
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
|
@ -145,3 +145,19 @@ when false:
|
||||||
doAssert foobar1(3) == OSDEF * 3
|
doAssert foobar1(3) == OSDEF * 3
|
||||||
when false: # Error: undeclared identifier: 'foobar2'
|
when false: # Error: undeclared identifier: 'foobar2'
|
||||||
doAssert foobar2(3) == 3 + 1
|
doAssert foobar2(3) == 3 + 1
|
||||||
|
|
||||||
|
# Double pointer
|
||||||
|
var
|
||||||
|
dv: DVOIDPTR
|
||||||
|
di: DINTPTR
|
||||||
|
ds: dstruct
|
||||||
|
cstr = "Hello".cstring
|
||||||
|
ds2: DSTRUCT2
|
||||||
|
|
||||||
|
dv = addr vptr
|
||||||
|
di = addr iptr
|
||||||
|
|
||||||
|
ds.field1 = di
|
||||||
|
ds2.field1 = addr cstr
|
||||||
|
ds2.tcv = test_call10
|
||||||
|
check ds2.tcv(di) == nil
|
||||||
Loading…
Add table
Add a link
Reference in a new issue