Skip to content

HTTPS clone URL

Subversion checkout URL

You can clone with
or
.
Download ZIP
Browse files

.

  • Loading branch information...
commit 356ed6f09c7dfb5d0f97d74b529379c53699084d 1 parent 5f3d0fb
@ccgus authored
Showing with 59 additions and 59 deletions.
  1. +2 −0  src/JSTFunction.h
  2. +40 −49 src/JSTFunction.m
  3. +17 −10 src/JSTTextView.m
View
2  src/JSTFunction.h
@@ -27,6 +27,8 @@
NSString *_forcedObjcSelector;
ffi_type **_encodedArgsForUnbridgedMsgSend;
+
+ BOOL _callingStret;
}
- (id)initWithFunctionName:(NSString*)name bridge:(JSTBridge*)bridge runtimeInfo:(JSTRuntimeInfo*)runtimeInfo;
View
89 src/JSTFunction.m
@@ -205,47 +205,17 @@ - (ffi_type **)_argsWithEncodeString: (const char *)str getCount: (int *)outCoun
return argTypes;
}
-- (int)_prepCIF: (ffi_cif *)cif withEncodeString: (const char *)str skipArg: (BOOL)skip
-{
- int argCount;
- ffi_type **argTypes = [self _argsWithEncodeString: str getCount: &argCount];
-
- if(skip)
- {
- argTypes++;
- argCount--;
- }
-
- ffi_status status = ffi_prep_cif(cif, FFI_DEFAULT_ABI, argCount, [self _ffiArgForEncode: str], argTypes);
- if(status != FFI_OK)
- {
- NSLog(@"Got result %ld from ffi_prep_cif", (long)status);
- abort();
- }
-
- return argCount;
-}
-
-
-- (void)_prepClosure {
- ffi_status status = ffi_prep_closure(_closure, &_closureCIF, BlockClosure, self);
- if(status != FFI_OK)
- {
- NSLog(@"ffi_prep_closure returned %d", (int)status);
- abort();
- }
-
- if(mprotect(_closure, sizeof(_closure), PROT_READ | PROT_EXEC) == -1)
- {
- perror("mprotect");
- abort();
- }
-}
-
- (void)setArguments:(const JSValueRef *)args withCount:(size_t)count {
_jsArguments = (JSValueRef *)args;
_argumentCount = count;
+ /*
+ for (int i = 0; i < count; i++) {
+ debug(@"in arg: '%@'", JSTNSObjectFromValue(_bridge, args[i]));
+ }
+ */
+
+
if (_forcedObjcTarget) {
JSValueRef *newArgs = malloc(sizeof(JSValueRef *) * (_argumentCount + 2));
@@ -315,7 +285,7 @@ - (Method)objcMethod {
return _objcMethod;
}
- JSTAssert((_callAddress == &objc_msgSend));
+ //JSTAssert((_callAddress == &objc_msgSend));
JSTAssert(_argumentCount > 1);
id target = JSTNSObjectFromValue(_bridge, _jsArguments[0]);
@@ -371,6 +341,7 @@ -(ffi_type*)setupReturnType {
if (retType == &ffi_type_jst_structure) {
debug(@"we need to setup for a struct");
_callAddress = &objc_msgSend_stret;
+ _callingStret = YES;
return [self encodingsForStructure:[[_msgSendMethodRuntimeInfo returnValue] typeEncoding]];
}
}
@@ -404,7 +375,6 @@ -(ffi_type*)setupReturnType {
return [self encodingsForStructure:[[info returnValue] typeEncoding]];
}
-
return JSTFFITypeForTypeEncoding([[info returnValue] typeEncoding]);
}
@@ -413,18 +383,18 @@ -(ffi_type*)setupReturnType {
-(ffi_type*)setValue:(void**)argVals atIndex:(int)idx {
- JSValueRef argument = _jsArguments[idx];
+ JSValueRef argument = _jsArguments[_callingStret ? idx - 1 : idx];
- if (_msgSendMethodRuntimeInfo || (_callAddress == &objc_msgSend)) {
+ if (_msgSendMethodRuntimeInfo || (_callAddress == &objc_msgSend) || _callingStret) {
void **foo = [self _allocate:(sizeof(void*))];
- if (idx == 0) { // this is the target
+ if (idx == 0 || (_callingStret && idx == 1)) { // this is the target
*foo = JSTNSObjectFromValue(_bridge, argument);
argVals[idx] = foo;
return &ffi_type_pointer;
}
- else if (idx == 1) { // arg 2 is always a selector
+ else if (idx == 1 || (_callingStret && idx == 2)) { // arg 2 is always a selector
*foo = JSTSelectorFromValue(_bridge, argument);
debug(@"selector: '%@'", NSStringFromSelector(*foo));
@@ -574,20 +544,35 @@ - (JSValueRef)call:(JSValueRef*)exception {
[self checkForMsgSendMethodRuntimeInfo];
- debug(@"Calling %@", _functionName);
+ ffi_type *returnFIIType = [self setupReturnType];
+
+ // objc_msgSend_stret returns void, and the return value is allocated on the stack, and a pointer passed as the first argument to it.
+ // thus, we must perform some gymnastics got get it working right.
+ size_t argumentCount = _callingStret ? _argumentCount + 1 : _argumentCount;
BOOL success = YES;
- ffi_type **argTypes = _argumentCount ? malloc(_argumentCount * sizeof(ffi_type*)) : 0x00;
- void **argVals = _argumentCount ? malloc(_argumentCount * sizeof(void*)) : 0x00;
+ ffi_type **argTypes = argumentCount ? malloc(argumentCount * sizeof(ffi_type*)) : 0x00;
+ void **argVals = argumentCount ? malloc(argumentCount * sizeof(void*)) : 0x00;
+ int j = _callingStret ? 1 : 0;
- for (int j = 0; j < _argumentCount; j++) {
+ for (; j < argumentCount; j++) {
argTypes[j] = [self setValue:*(void**)&argVals atIndex:j];
}
- ffi_type *returnFIIType = [self setupReturnType];
+ NSRect stretwtf;
+
+ if (_callingStret) {
+ void *f = &stretwtf;
+ argVals[0] = &f;
+ argTypes[0] = &ffi_type_pointer;
+
+ //argTypes[0] = [self setValue:&f atIndex:0];
+
+ returnFIIType = &ffi_type_void;
+ }
ffi_cif cif;
- ffi_status status = ffi_prep_cif(&cif, FFI_DEFAULT_ABI, (unsigned)_argumentCount, returnFIIType, argTypes);
+ ffi_status status = ffi_prep_cif(&cif, FFI_DEFAULT_ABI, (unsigned)argumentCount, returnFIIType, argTypes);
if (status != FFI_OK) {
if (status == FFI_BAD_TYPEDEF) {
debug(@"FFI_BAD_TYPEDEF");
@@ -605,13 +590,19 @@ - (JSValueRef)call:(JSValueRef*)exception {
void *returnValue;
@try {
+ debug(@"%s:%d", __FUNCTION__, __LINE__);
ffi_call(&cif, _callAddress, &returnValue, argVals);
+ debug(@"%s:%d", __FUNCTION__, __LINE__);
}
@catch (NSException * e) {
success = NO;
JSTAssignException(_bridge, exception, [e description]);
}
+ if (_callingStret) {
+ debug(@"stretwtf: %@", NSStringFromRect(stretwtf));
+ }
+
if (argTypes) {
free(argTypes);
}
View
27 src/JSTTextView.m
@@ -173,10 +173,13 @@ - (void)insertText:(id)insertString {
[super insertText:insertString];
NSRange currentRange = [self selectedRange];
+ NSRange r = [self selectionRangeForProposedRange:currentRange granularity:NSSelectByParagraph];
+ BOOL atEndOfLine = (NSMaxRange(r) - 1 == NSMaxRange(currentRange));
- if ([@"{" isEqualToString:insertString]) {
+
+ if (atEndOfLine && [@"{" isEqualToString:insertString]) {
- NSRange r = [self selectionRangeForProposedRange:currentRange granularity:NSSelectByParagraph];
+ r = [self selectionRangeForProposedRange:currentRange granularity:NSSelectByParagraph];
NSString *myLine = [[[self textStorage] mutableString] substringWithRange:r];
NSMutableString *indent = [NSMutableString string];
@@ -194,20 +197,24 @@ - (void)insertText:(id)insertString {
[self setSelectedRange:currentRange];
}
- else if ([@"(" isEqualToString:insertString]) {
+ else if (atEndOfLine && [@"(" isEqualToString:insertString]) {
- // make sure to only do it on the end of the line.
- NSRange r = [self selectionRangeForProposedRange:currentRange granularity:NSSelectByParagraph];
- if (NSMaxRange(r) - 1 == NSMaxRange(currentRange)) {
- [super insertText:@")"];
- [self setSelectedRange:currentRange];
- }
+ [super insertText:@")"];
+ [self setSelectedRange:currentRange];
}
- else if ([@"[" isEqualToString:insertString]) {
+ else if (atEndOfLine && [@"[" isEqualToString:insertString]) {
[super insertText:@"]"];
[self setSelectedRange:currentRange];
}
+ else if ([@"\"" isEqualToString:insertString]) {
+ [super insertText:@"\""];
+ [self setSelectedRange:currentRange];
+ }
+ else if ([@"'" isEqualToString:insertString]) {
+ [super insertText:@"'"];
+ [self setSelectedRange:currentRange];
+ }
}
- (void)insertTab:(id)sender {
Please sign in to comment.
Something went wrong with that request. Please try again.