Skip to content

Commit e3acd13

Browse files
committed
[WebIDL] Generate correct code when a pointer is returned from an interface method
1 parent 8cc1654 commit e3acd13

File tree

8 files changed

+83
-4
lines changed

8 files changed

+83
-4
lines changed

AUTHORS

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -598,3 +598,4 @@ a license to everyone to use it as detailed in LICENSE.)
598598
* Jerry Zhuang <[email protected]>
599599
* Taisei Kon <[email protected]>
600600
* YAMAMOTO Takashi <[email protected]>
601+
* Artur Gatin <[email protected]> (copyright owned by Teladoc Health, Inc.)

test/webidl/post.js

Lines changed: 14 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -243,6 +243,20 @@ try {
243243
s.Print(123, null); // Expects a string or a wrapped pointer
244244
} catch (e) {}
245245

246+
// Returned pointers (issue 14745)
247+
248+
var factory = new TheModule.ObjectFactory();
249+
var objectProvider = factory.getProvider();
250+
var smallObject = objectProvider.getObject();
251+
252+
// This will print 123 if we managed to access the object, which means that integers
253+
// were correctly typecast to ObjectProvider pointer and SmallObject pointer.
254+
console.log(smallObject.getID(123));
255+
256+
TheModule.destroy(factory)
257+
258+
// end of issue 14745
259+
246260
// Check for overflowing the stack
247261

248262
var before = Date.now();
@@ -285,7 +299,5 @@ if (isMemoryGrowthAllowed) {
285299
}
286300
}
287301

288-
//
289-
290302
console.log('\ndone.')
291303
})();

test/webidl/test.h

Lines changed: 35 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -194,3 +194,38 @@ typedef struct LongLongTypes {
194194
unsigned long long* lluArray;
195195
long long ll;
196196
} LongLongTypes;
197+
198+
// Returning child objects in a hierarchy
199+
200+
struct ISmallObject {
201+
virtual int getID(int number) = 0;
202+
};
203+
204+
struct IObjectProvider {
205+
virtual ISmallObject* getObject() = 0;
206+
};
207+
208+
class SmallObject : public ISmallObject {
209+
public:
210+
int getID(int number) {
211+
return number;
212+
}
213+
};
214+
215+
class ObjectProvider : public IObjectProvider {
216+
public:
217+
ISmallObject* getObject() {
218+
return &m_smallObject;
219+
}
220+
private:
221+
SmallObject m_smallObject;
222+
};
223+
224+
class ObjectFactory {
225+
public:
226+
IObjectProvider* getProvider() {
227+
return &m_ObjectProvider;
228+
}
229+
private:
230+
ObjectProvider m_ObjectProvider;
231+
};

test/webidl/test.idl

Lines changed: 27 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -169,3 +169,30 @@ interface LongLongTypes {
169169
readonly attribute unsigned long long[] lluArray;
170170
attribute long long ll;
171171
};
172+
173+
[NoDelete]
174+
interface ISmallObject {
175+
long getID(long number);
176+
};
177+
178+
[JSImplementation="ISmallObject"]
179+
interface JSSmallObject {
180+
void JSSmallObject();
181+
long getID(long number);
182+
};
183+
184+
[NoDelete]
185+
interface IObjectProvider {
186+
ISmallObject getObject();
187+
};
188+
189+
[JSImplementation="IObjectProvider"]
190+
interface JSObjectProvider {
191+
void JSObjectProvider();
192+
JSSmallObject getObject();
193+
};
194+
195+
interface ObjectFactory {
196+
void ObjectFactory();
197+
IObjectProvider getProvider();
198+
};

test/webidl/test_ALL.out

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -109,3 +109,4 @@ Aborted(Assertion failed: [CHECK FAILED] Parent::Parent(val:val): Expecting <int
109109
Parent:42
110110
Aborted(Assertion failed: [CHECK FAILED] Parent::voidStar(something:something): Expecting <pointer>)
111111
Aborted(Assertion failed: [CHECK FAILED] StringUser::Print(anotherString:anotherString): Expecting <string>)
112+
123

test/webidl/test_DEFAULT.out

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -108,5 +108,6 @@ struct_ptr_array[0]->attr2 == 101
108108
Parent:0
109109
Parent:42
110110
|abc|1|(null)|123|
111+
123
111112

112113
done.

test/webidl/test_FAST.out

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -108,5 +108,6 @@ struct_ptr_array[0]->attr2 == 101
108108
Parent:0
109109
Parent:42
110110
|abc|1|(null)|123|
111+
123
111112

112113
done.

tools/webidl_binder.py

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -647,15 +647,16 @@ def make_call_args(i):
647647
if i == max_args:
648648
dec_args = ', '.join([type_to_cdec(raw[j]) + ' ' + args[j] for j in range(i)])
649649
js_call_args = ', '.join(['%s%s' % (('(ptrdiff_t)' if sig[j] in interfaces else '') + take_addr_if_nonpointer(raw[j]), args[j]) for j in range(i)])
650+
em_asm_macro = 'EM_ASM_%s' % ('PTR' if c_return_type[-1] == '*' else 'INT' if c_return_type not in C_FLOATS else 'DOUBLE')
650651

651652
js_impl_methods.append(r''' %s %s(%s) %s {
652-
%sEM_ASM_%s({
653+
%s (%s) %s({
653654
var self = Module['getCache'](Module['%s'])[$0];
654655
if (!self.hasOwnProperty('%s')) throw 'a JSImplementation must implement all functions, you forgot %s::%s.';
655656
%sself['%s'](%s)%s;
656657
}, (ptrdiff_t)this%s);
657658
}''' % (c_return_type, func_name, dec_args, maybe_const,
658-
basic_return, 'INT' if c_return_type not in C_FLOATS else 'DOUBLE',
659+
basic_return, c_return_type, em_asm_macro,
659660
class_name,
660661
func_name, class_name, func_name,
661662
return_prefix,

0 commit comments

Comments
 (0)