diff options
author | Benoit Germain <bnt.germain@gmail.com> | 2021-06-26 18:25:53 +0200 |
---|---|---|
committer | Benoit Germain <bnt.germain@gmail.com> | 2021-06-26 18:25:53 +0200 |
commit | 909470be9f7ec1dd2d09ae1a371d69c9c652e957 (patch) | |
tree | cd16d9976e90c1d8a61d8ee3423d4af1671bafc0 /deep_test | |
parent | 050e14dd7fa04e2262ae6b1cc984d76c4149b664 (diff) | |
download | lanes-909470be9f7ec1dd2d09ae1a371d69c9c652e957.tar.gz lanes-909470be9f7ec1dd2d09ae1a371d69c9c652e957.tar.bz2 lanes-909470be9f7ec1dd2d09ae1a371d69c9c652e957.zip |
fix stack overflow when transfering a clonable userdata referencing itself through a uservalue
Diffstat (limited to 'deep_test')
-rw-r--r-- | deep_test/deep_test.c | 2 | ||||
-rw-r--r-- | deep_test/deep_test.vcxproj | 5 | ||||
-rw-r--r-- | deep_test/deep_test.vcxproj.user | 6 | ||||
-rw-r--r-- | deep_test/deeptest.lua | 47 |
4 files changed, 46 insertions, 14 deletions
diff --git a/deep_test/deep_test.c b/deep_test/deep_test.c index dabc84d..873428b 100644 --- a/deep_test/deep_test.c +++ b/deep_test/deep_test.c | |||
@@ -16,6 +16,7 @@ | |||
16 | 16 | ||
17 | // ################################################################################################ | 17 | // ################################################################################################ |
18 | 18 | ||
19 | // a lanes-deep userdata. needs DeepPrelude and luaG_newdeepuserdata from Lanes code. | ||
19 | struct s_MyDeepUserdata | 20 | struct s_MyDeepUserdata |
20 | { | 21 | { |
21 | DeepPrelude prelude; // Deep userdata MUST start with this header | 22 | DeepPrelude prelude; // Deep userdata MUST start with this header |
@@ -190,6 +191,7 @@ static int clonable_gc( lua_State* L) | |||
190 | 191 | ||
191 | // ################################################################################################ | 192 | // ################################################################################################ |
192 | 193 | ||
194 | // this is all we need to make a userdata lanes-clonable. no dependency on Lanes code. | ||
193 | static int clonable_lanesclone( lua_State* L) | 195 | static int clonable_lanesclone( lua_State* L) |
194 | { | 196 | { |
195 | switch( lua_gettop( L)) | 197 | switch( lua_gettop( L)) |
diff --git a/deep_test/deep_test.vcxproj b/deep_test/deep_test.vcxproj index 67d3afd..6e25b9a 100644 --- a/deep_test/deep_test.vcxproj +++ b/deep_test/deep_test.vcxproj | |||
@@ -115,6 +115,10 @@ | |||
115 | <OutDir>$(SolutionDir)_Output\$(ProjectName)\$(PlatformName)\$(Configuration)\</OutDir> | 115 | <OutDir>$(SolutionDir)_Output\$(ProjectName)\$(PlatformName)\$(Configuration)\</OutDir> |
116 | <IntDir>$(SolutionDir)_Tmp\$(ProjectName)\$(PlatformName)\$(Configuration)\</IntDir> | 116 | <IntDir>$(SolutionDir)_Tmp\$(ProjectName)\$(PlatformName)\$(Configuration)\</IntDir> |
117 | </PropertyGroup> | 117 | </PropertyGroup> |
118 | <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release 5.3|x64'"> | ||
119 | <OutDir>$(SolutionDir)_Output\$(ProjectName)\$(PlatformName)\$(Configuration)\</OutDir> | ||
120 | <IntDir>$(SolutionDir)_Tmp\$(ProjectName)\$(PlatformName)\$(Configuration)\</IntDir> | ||
121 | </PropertyGroup> | ||
118 | <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release 5.3|x64'"> | 122 | <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release 5.3|x64'"> |
119 | <ClCompile> | 123 | <ClCompile> |
120 | <WarningLevel>Level3</WarningLevel> | 124 | <WarningLevel>Level3</WarningLevel> |
@@ -125,6 +129,7 @@ | |||
125 | <ConformanceMode>true</ConformanceMode> | 129 | <ConformanceMode>true</ConformanceMode> |
126 | <AdditionalIncludeDirectories>$(SolutionDir)Lanes\lanes\src;$(SolutionDir)..\lualib;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories> | 130 | <AdditionalIncludeDirectories>$(SolutionDir)Lanes\lanes\src;$(SolutionDir)..\lualib;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories> |
127 | <ProgramDataBaseFileName>$(IntDir)$(TargetName).pdb</ProgramDataBaseFileName> | 131 | <ProgramDataBaseFileName>$(IntDir)$(TargetName).pdb</ProgramDataBaseFileName> |
132 | <PreprocessorDefinitions>_WINDLL;_CRT_SECURE_NO_WARNINGS;%(PreprocessorDefinitions)</PreprocessorDefinitions> | ||
128 | </ClCompile> | 133 | </ClCompile> |
129 | <Link> | 134 | <Link> |
130 | <EnableCOMDATFolding>true</EnableCOMDATFolding> | 135 | <EnableCOMDATFolding>true</EnableCOMDATFolding> |
diff --git a/deep_test/deep_test.vcxproj.user b/deep_test/deep_test.vcxproj.user index 70871df..9195f89 100644 --- a/deep_test/deep_test.vcxproj.user +++ b/deep_test/deep_test.vcxproj.user | |||
@@ -12,4 +12,10 @@ | |||
12 | <LocalDebuggerCommandArguments>-i deeptest.lua</LocalDebuggerCommandArguments> | 12 | <LocalDebuggerCommandArguments>-i deeptest.lua</LocalDebuggerCommandArguments> |
13 | <LocalDebuggerWorkingDirectory>D:\Boulot\anubis\Lua\bindings\Lanes\lanes\deep_test\</LocalDebuggerWorkingDirectory> | 13 | <LocalDebuggerWorkingDirectory>D:\Boulot\anubis\Lua\bindings\Lanes\lanes\deep_test\</LocalDebuggerWorkingDirectory> |
14 | </PropertyGroup> | 14 | </PropertyGroup> |
15 | <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release 5.3|x64'"> | ||
16 | <LocalDebuggerCommand>D:\Boulot\anubis\Lua\framework\lua53.exe</LocalDebuggerCommand> | ||
17 | <DebuggerFlavor>WindowsLocalDebugger</DebuggerFlavor> | ||
18 | <LocalDebuggerCommandArguments>-i -- deeptest.lua</LocalDebuggerCommandArguments> | ||
19 | <LocalDebuggerWorkingDirectory>D:\Boulot\anubis\Lua\bindings\Lanes\lanes\deep_test\</LocalDebuggerWorkingDirectory> | ||
20 | </PropertyGroup> | ||
15 | </Project> \ No newline at end of file | 21 | </Project> \ No newline at end of file |
diff --git a/deep_test/deeptest.lua b/deep_test/deeptest.lua index 92cd372..3c89c3d 100644 --- a/deep_test/deeptest.lua +++ b/deep_test/deeptest.lua | |||
@@ -5,8 +5,8 @@ local l = lanes.linda "my linda" | |||
5 | local dt = lanes.require "deep_test" | 5 | local dt = lanes.require "deep_test" |
6 | 6 | ||
7 | local test_deep = true | 7 | local test_deep = true |
8 | local test_clonable = false | 8 | local test_clonable = true |
9 | local test_uvtype = "string" | 9 | local test_uvtype = "function" |
10 | 10 | ||
11 | local makeUserValue = function( obj_) | 11 | local makeUserValue = function( obj_) |
12 | if test_uvtype == "string" then | 12 | if test_uvtype == "string" then |
@@ -14,12 +14,23 @@ local makeUserValue = function( obj_) | |||
14 | elseif test_uvtype == "function" then | 14 | elseif test_uvtype == "function" then |
15 | -- a function that pull the userdata as upvalue | 15 | -- a function that pull the userdata as upvalue |
16 | local f = function() | 16 | local f = function() |
17 | print( obj_) | 17 | return tostring( obj_) |
18 | end | 18 | end |
19 | return f | 19 | return f |
20 | end | 20 | end |
21 | end | 21 | end |
22 | 22 | ||
23 | local printDeep = function( prefix_, obj_, t_) | ||
24 | local uservalue = obj_:getuv( 1) | ||
25 | print( prefix_) | ||
26 | print ( obj_, uservalue, type( uservalue) == "function" and uservalue() or "") | ||
27 | if t_ then | ||
28 | for k, v in pairs( t_) do | ||
29 | print( k, v) | ||
30 | end | ||
31 | end | ||
32 | end | ||
33 | |||
23 | local performTest = function( obj_) | 34 | local performTest = function( obj_) |
24 | -- setup the userdata with some value and a uservalue | 35 | -- setup the userdata with some value and a uservalue |
25 | obj_:set( 666) | 36 | obj_:set( 666) |
@@ -29,15 +40,20 @@ local performTest = function( obj_) | |||
29 | -- lua 5.4 supports multiple uservalues of arbitrary types | 40 | -- lua 5.4 supports multiple uservalues of arbitrary types |
30 | -- obj_:setuv( 2, "ENDUV") | 41 | -- obj_:setuv( 2, "ENDUV") |
31 | 42 | ||
43 | local t = | ||
44 | { | ||
45 | ["key"] = obj_, | ||
46 | -- [obj_] = "val" | ||
47 | } | ||
48 | |||
32 | -- read back the contents of the object | 49 | -- read back the contents of the object |
33 | print( "immediate:", obj_, obj_:getuv( 1)) | 50 | printDeep( "immediate:", obj_, t) |
34 | 51 | ||
35 | -- send the object in a linda, get it back out, read the contents | 52 | -- send the object in a linda, get it back out, read the contents |
36 | l:set( "key", obj_) | 53 | l:set( "key", obj_, t) |
37 | -- when obj_ is a deep userdata, out is the same userdata as obj_ (not another one pointing on the same deep memory block) because of an internal cache table [deep*] -> proxy) | 54 | -- when obj_ is a deep userdata, out is the same userdata as obj_ (not another one pointing on the same deep memory block) because of an internal cache table [deep*] -> proxy) |
38 | -- when obj_ is a clonable userdata, we get a different clone everytime we cross a linda or lane barrier | 55 | -- when obj_ is a clonable userdata, we get a different clone everytime we cross a linda or lane barrier |
39 | local out = l:get( "key") | 56 | printDeep( "out of linda:", l:get( "key", 2)) |
40 | print( "out of linda:", out, out:getuv( 1)) | ||
41 | 57 | ||
42 | -- send the object in a lane through parameter passing, the lane body returns it as return value, read the contents | 58 | -- send the object in a lane through parameter passing, the lane body returns it as return value, read the contents |
43 | local g = lanes.gen( | 59 | local g = lanes.gen( |
@@ -45,23 +61,26 @@ local performTest = function( obj_) | |||
45 | , { | 61 | , { |
46 | required = { "deep_test"} -- we will transfer userdata created by this module, so we need to make this lane aware of it | 62 | required = { "deep_test"} -- we will transfer userdata created by this module, so we need to make this lane aware of it |
47 | } | 63 | } |
48 | , function( param_) | 64 | , function( arg_, t_) |
49 | -- read contents inside lane | 65 | -- read contents inside lane: arg_ and t_ by argument |
50 | print( "in lane:", param_, param_:getuv( 1)) | 66 | printDeep( "in lane, as arguments:", arg_, t_) |
51 | return param_ | 67 | -- read contents inside lane: obj_ and t by upvalue |
68 | printDeep( "in lane, as upvalues:", obj_, t) | ||
69 | return arg_, t_ | ||
52 | end | 70 | end |
53 | ) | 71 | ) |
54 | h = g( obj_) | 72 | h = g( obj_, t) |
55 | -- when obj_ is a deep userdata, from_lane is the same userdata as obj_ (not another one pointing on the same deep memory block) because of an internal cache table [deep*] -> proxy) | 73 | -- when obj_ is a deep userdata, from_lane is the same userdata as obj_ (not another one pointing on the same deep memory block) because of an internal cache table [deep*] -> proxy) |
56 | -- when obj_ is a clonable userdata, we get a different clone everytime we cross a linda or lane barrier | 74 | -- when obj_ is a clonable userdata, we get a different clone everytime we cross a linda or lane barrier |
57 | local from_lane = h[1] | 75 | printDeep( "from lane:", h[1], h[2]) |
58 | print( "from lane:", from_lane, from_lane:getuv( 1)) | ||
59 | end | 76 | end |
60 | 77 | ||
61 | if test_deep then | 78 | if test_deep then |
79 | print "DEEP" | ||
62 | performTest( dt.new_deep()) | 80 | performTest( dt.new_deep()) |
63 | end | 81 | end |
64 | 82 | ||
65 | if test_clonable then | 83 | if test_clonable then |
84 | print "CLONABLE" | ||
66 | performTest( dt.new_clonable()) | 85 | performTest( dt.new_clonable()) |
67 | end | 86 | end |