]> git.saurik.com Git - cycript.git/commitdiff
Support round trip of signed char through typedef.
authorJay Freeman (saurik) <saurik@saurik.com>
Mon, 28 Dec 2015 02:13:19 +0000 (18:13 -0800)
committerJay Freeman (saurik) <saurik@saurik.com>
Mon, 28 Dec 2015 02:13:19 +0000 (18:13 -0800)
Decode.cpp
Execute.cpp
JavaScript.hpp
ObjectiveC/Library.mm
sig/ffi_type.cpp
sig/parse.cpp
sig/types.hpp

index bcf77132ce27976aebdaaa3fa1348827a00b91f2..acf8b957dacb517f6fb0cf3f3cd7d19de6ebea35 100644 (file)
@@ -77,7 +77,7 @@ CYTypedIdentifier *Decode_(CYPool &pool, struct sig::Type *type) {
         } break;
 
         case sig::bit_P: _assert(false); break;
-        case sig::char_P: return $ CYTypedIdentifier($ CYTypeVariable("char"));
+        case sig::schar_P: return $ CYTypedIdentifier($ CYTypeSigned($ CYTypeVariable("char")));
         case sig::double_P: return $ CYTypedIdentifier($ CYTypeVariable("double"));
         case sig::float_P: return $ CYTypedIdentifier($ CYTypeVariable("float"));
         case sig::int_P: return $ CYTypedIdentifier($ CYTypeVariable("int"));
@@ -86,6 +86,7 @@ CYTypedIdentifier *Decode_(CYPool &pool, struct sig::Type *type) {
         case sig::short_P: return $ CYTypedIdentifier($ CYTypeShort($ CYTypeVariable("int")));
 
         case sig::void_P: return $ CYTypedIdentifier($ CYTypeVoid());
+        case sig::char_P: return $ CYTypedIdentifier($ CYTypeVariable("char"));
 
         case sig::struct_P: {
             CYTypeStructField *fields(NULL);
index 1c83e26e9252cec2b189c249321e96cf82faca90..af4f3668a73a40b676eae48c17f449438bba7a9d 100644 (file)
@@ -662,7 +662,7 @@ void CYPoolFFI(CYPool *pool, JSContextRef context, sig::Type *type, ffi_type *ff
         break;
 
         CYPoolFFI_(uchar, unsigned char)
-        CYPoolFFI_(char, char)
+        CYPoolFFI_(schar, signed char)
         CYPoolFFI_(ushort, unsigned short)
         CYPoolFFI_(short, short)
         CYPoolFFI_(ulong, unsigned long)
@@ -737,6 +737,9 @@ void CYPoolFFI(CYPool *pool, JSContextRef context, sig::Type *type, ffi_type *ff
         case sig::void_P:
         break;
 
+        // XXX: implement a conversion from a single character string?
+        CYPoolFFI_(char, char)
+
         default:
             for (CYHook *hook : GetHooks())
                 if (hook->PoolFFI != NULL)
@@ -757,7 +760,7 @@ JSValueRef CYFromFFI(JSContextRef context, sig::Type *type, ffi_type *ffi, void
             return CYCastJSValue(context, *reinterpret_cast<native *>(data)); \
 
         CYFromFFI_(uchar, unsigned char)
-        CYFromFFI_(char, char)
+        CYFromFFI_(schar, signed char)
         CYFromFFI_(ushort, unsigned short)
         CYFromFFI_(short, short)
         CYFromFFI_(ulong, unsigned long)
@@ -789,6 +792,8 @@ JSValueRef CYFromFFI(JSContextRef context, sig::Type *type, ffi_type *ffi, void
         case sig::void_P:
             return CYJSUndefined(context);
 
+        CYFromFFI_(char, char)
+
         null:
             return CYJSNull(context);
         default:
@@ -1114,8 +1119,8 @@ static JSValueRef Pointer_callAsFunction(JSContextRef context, JSObjectRef objec
     return CYCallAsFunction(context, functor, _this, count, arguments);
 } CYCatch(NULL) }
 
-JSObjectRef CYMakeType(JSContextRef context, const char *encoding) {
-    Type_privateData *internal(new Type_privateData(encoding));
+JSObjectRef CYMakeType(JSContextRef context, sig::Primitive primitive) {
+    Type_privateData *internal(new Type_privateData(primitive));
     return JSObjectMake(context, Type_privateData::Class_, internal);
 }
 
@@ -1310,8 +1315,10 @@ static JSObjectRef Type_new(JSContextRef context, JSObjectRef object, size_t cou
 
     if (false) {
     } else if (count == 1) {
-        const char *type(CYPoolCString(pool, context, arguments[0]));
-        return CYMakeType(context, type);
+        const char *encoding(CYPoolCString(pool, context, arguments[0]));
+        sig::Signature signature;
+        sig::Parse(pool, &signature, encoding, &Structor_);
+        return CYMakeType(context, signature.elements[0].type);
     } else if (count == 2) {
         JSObjectRef types(CYCastJSObject(context, arguments[0]));
         size_t count(CYArrayLength(context, types));
@@ -1457,7 +1464,7 @@ static JSValueRef Type_callAsFunction_signed(JSContextRef context, JSObjectRef o
     sig::Type type(*internal->type_);
 
     switch (type.primitive) {
-        case sig::char_P: case sig::uchar_P: type.primitive = sig::char_P; break;
+        case sig::char_P: case sig::schar_P: case sig::uchar_P: type.primitive = sig::schar_P; break;
         case sig::short_P: case sig::ushort_P: type.primitive = sig::short_P; break;
         case sig::int_P: case sig::uint_P: type.primitive = sig::int_P; break;
         case sig::long_P: case sig::ulong_P: type.primitive = sig::long_P; break;
@@ -1476,7 +1483,7 @@ static JSValueRef Type_callAsFunction_unsigned(JSContextRef context, JSObjectRef
     sig::Type type(*internal->type_);
 
     switch (type.primitive) {
-        case sig::char_P: case sig::uchar_P: type.primitive = sig::uchar_P; break;
+        case sig::char_P: case sig::schar_P: case sig::uchar_P: type.primitive = sig::uchar_P; break;
         case sig::short_P: case sig::ushort_P: type.primitive = sig::ushort_P; break;
         case sig::int_P: case sig::uint_P: type.primitive = sig::uint_P; break;
         case sig::long_P: case sig::ulong_P: type.primitive = sig::ulong_P; break;
@@ -2274,13 +2281,13 @@ extern "C" void CYSetupContext(JSGlobalContextRef context) {
 
     CYSetProperty(context, cache, CYJSString("NULL"), CYJSNull(context), kJSPropertyAttributeDontEnum);
 
-    CYSetProperty(context, cache, CYJSString("bool"), CYMakeType(context, "B"), kJSPropertyAttributeDontEnum);
-    CYSetProperty(context, cache, CYJSString("char"), CYMakeType(context, "c"), kJSPropertyAttributeDontEnum);
-    CYSetProperty(context, cache, CYJSString("short"), CYMakeType(context, "s"), kJSPropertyAttributeDontEnum);
-    CYSetProperty(context, cache, CYJSString("int"), CYMakeType(context, "i"), kJSPropertyAttributeDontEnum);
-    CYSetProperty(context, cache, CYJSString("long"), CYMakeType(context, "l"), kJSPropertyAttributeDontEnum);
-    CYSetProperty(context, cache, CYJSString("float"), CYMakeType(context, "f"), kJSPropertyAttributeDontEnum);
-    CYSetProperty(context, cache, CYJSString("double"), CYMakeType(context, "d"), kJSPropertyAttributeDontEnum);
+    CYSetProperty(context, cache, CYJSString("bool"), CYMakeType(context, sig::boolean_P), kJSPropertyAttributeDontEnum);
+    CYSetProperty(context, cache, CYJSString("char"), CYMakeType(context, sig::char_P), kJSPropertyAttributeDontEnum);
+    CYSetProperty(context, cache, CYJSString("short"), CYMakeType(context, sig::short_P), kJSPropertyAttributeDontEnum);
+    CYSetProperty(context, cache, CYJSString("int"), CYMakeType(context, sig::int_P), kJSPropertyAttributeDontEnum);
+    CYSetProperty(context, cache, CYJSString("long"), CYMakeType(context, sig::long_P), kJSPropertyAttributeDontEnum);
+    CYSetProperty(context, cache, CYJSString("float"), CYMakeType(context, sig::float_P), kJSPropertyAttributeDontEnum);
+    CYSetProperty(context, cache, CYJSString("double"), CYMakeType(context, sig::double_P), kJSPropertyAttributeDontEnum);
 
     for (CYHook *hook : GetHooks())
         if (hook->SetupContext != NULL)
index 33b3db8bd674ce22716f6b90e05eb1ce4e027b75..074c7db3a2cc5c6132797c3daae2591e5f20f5dc 100644 (file)
@@ -143,7 +143,7 @@ struct CYRegisterHook {
 
 JSObjectRef CYMakePointer(JSContextRef context, void *pointer, size_t length, sig::Type *type, ffi_type *ffi, JSObjectRef owner);
 
-JSObjectRef CYMakeType(JSContextRef context, const char *encoding);
+JSObjectRef CYMakeType(JSContextRef context, sig::Primitive primitive);
 JSObjectRef CYMakeType(JSContextRef context, sig::Type *type);
 JSObjectRef CYMakeType(JSContextRef context, sig::Signature *signature);
 
index 177ff6f8711efcf6cdb1e0e973fd8d76e31d6b55..0fb792a07bc812e79b213e056e2c7c4da3871751 100644 (file)
@@ -3033,9 +3033,9 @@ void CYObjectiveC_SetupContext(JSContextRef context) { CYPoolTry {
     JSObjectRef cache(CYGetCachedObject(context, CYJSString("cache")));
     CYSetProperty(context, cache, CYJSString("YES"), JSValueMakeBoolean(context, true), kJSPropertyAttributeDontEnum);
     CYSetProperty(context, cache, CYJSString("NO"), JSValueMakeBoolean(context, false), kJSPropertyAttributeDontEnum);
-    CYSetProperty(context, cache, CYJSString("id"), CYMakeType(context, "@"), kJSPropertyAttributeDontEnum);
-    CYSetProperty(context, cache, CYJSString("Class"), CYMakeType(context, "#"), kJSPropertyAttributeDontEnum);
-    CYSetProperty(context, cache, CYJSString("SEL"), CYMakeType(context, ":"), kJSPropertyAttributeDontEnum);
+    CYSetProperty(context, cache, CYJSString("id"), CYMakeType(context, sig::object_P), kJSPropertyAttributeDontEnum);
+    CYSetProperty(context, cache, CYJSString("Class"), CYMakeType(context, sig::typename_P), kJSPropertyAttributeDontEnum);
+    CYSetProperty(context, cache, CYJSString("SEL"), CYMakeType(context, sig::selector_P), kJSPropertyAttributeDontEnum);
 } CYPoolCatch() }
 
 static void *CYObjectiveC_CastSymbol(const char *name) {
index 836f7cd8bb938e2e5ab95da4b0c7826030ff1a09..b75d6066feb665ec4df18d054028c7a27192ad7e 100644 (file)
@@ -87,7 +87,7 @@ ffi_type *ObjectiveC(CYPool &pool, struct Type *type) {
             _assert(false);
         break;
 
-        case char_P: return &ffi_type_schar;
+        case schar_P: return &ffi_type_schar;
         case double_P: return &ffi_type_double;
         case float_P: return &ffi_type_float;
         case int_P: return &ffi_type_sint;
@@ -96,6 +96,7 @@ ffi_type *ObjectiveC(CYPool &pool, struct Type *type) {
         case short_P: return &ffi_type_sshort;
 
         case void_P: return &ffi_type_void;
+        case char_P: return &ffi_type_schar;
 
         case struct_P: {
             ffi_type *aggregate(new(pool) ffi_type());
@@ -133,7 +134,7 @@ ffi_type *Java(CYPool &pool, struct Type *type) {
         case array_P: return &ffi_type_pointer;
         case pointer_P: return &ffi_type_pointer;
         case bit_P: _assert(false); break;
-        case char_P: return &ffi_type_schar;
+        case schar_P: return &ffi_type_schar;
         case double_P: return &ffi_type_double;
         case float_P: return &ffi_type_double;
         case int_P: return &ffi_type_sint;
@@ -141,6 +142,7 @@ ffi_type *Java(CYPool &pool, struct Type *type) {
         case longlong_P: return &ffi_type_slonglong;
         case short_P: return &ffi_type_sshort;
         case void_P: return &ffi_type_void;
+        case char_P: return &ffi_type_schar;
         case struct_P: return &ffi_type_pointer;
 
         default:
index 62d99cff314e0ad22806614d672755765c22203a..67a28bf633fc0ab6fd5e1d481d5269b53cec1a05 100644 (file)
@@ -160,7 +160,7 @@ Type *Parse_(CYPool &pool, const char **name, char eos, bool named, Callback cal
             type->data.data.size = strtoul(*name, (char **) name, 10);
         break;
 
-        case 'c': type->primitive = char_P; break;
+        case 'c': type->primitive = schar_P; break;
         case 'd': type->primitive = double_P; break;
         case 'f': type->primitive = float_P; break;
         case 'i': type->primitive = int_P; break;
@@ -286,7 +286,7 @@ const char *Unparse_(CYPool &pool, struct Type *type) {
         } break;
 
         case bit_P: return pool.strcat("b", pool.itoa(type->data.data.size), NULL);
-        case char_P: return "c";
+        case schar_P: return "c";
         case double_P: return "d";
         case float_P: return "f";
         case int_P: return "i";
@@ -294,6 +294,7 @@ const char *Unparse_(CYPool &pool, struct Type *type) {
         case longlong_P: return "q";
         case short_P: return "s";
         case void_P: return "v";
+        case char_P: return "c";
         case struct_P: return pool.strcat("{", type->name == NULL ? "?" : type->name, "=", Unparse(pool, &type->data.signature), "}", NULL);
     }
 
index 175d172c679ee086754371c13a010cc550f2b609..7bf83b8e579fbb26a884c24a633a6adbcded63e3 100644 (file)
@@ -32,6 +32,7 @@ namespace sig {
 enum Primitive {
     function_P = '\0',
     block_P = '\a',
+    char_P = '\b',
 
     unknown_P = '?',
     typename_P = '#',
@@ -48,7 +49,7 @@ enum Primitive {
     array_P = '[',
     pointer_P = '^',
     bit_P = 'b',
-    char_P = 'c',
+    schar_P = 'c',
     double_P = 'd',
     float_P = 'f',
     int_P = 'i',