Firefox addon Mac OS X-CoreFoundation-读取字典值

Firefox addon Mac OS X-CoreFoundation-读取字典值,firefox-addon,jsctypes,Firefox Addon,Jsctypes,我试图帮助别人,所以我写了一些ctypes来检查工作站是否被锁定 我正在成功地获取此信息,但无法从字典中读取值 这段代码在我需要将获得的值转换为字符串的时候一直正常运行。查看注释//读取值我在注释中输入了它抛出的错误 Cu.import('resource://gre/modules/ctypes.jsm'); var lib = { CoreGraphics: '/System/Library/Frameworks/CoreGraphics.framework/CoreGraphics',

我试图帮助别人,所以我写了一些ctypes来检查工作站是否被锁定

我正在成功地获取此信息,但无法从字典中读取值

这段代码在我需要将获得的值转换为字符串的时候一直正常运行。查看注释
//读取值
我在注释中输入了它抛出的错误

Cu.import('resource://gre/modules/ctypes.jsm');
var lib = {
  CoreGraphics: '/System/Library/Frameworks/CoreGraphics.framework/CoreGraphics',
  CoreFoundation: '/System/Library/Frameworks/CoreFoundation.framework/CoreFoundation'
};
for (var l in lib) {
  lib[l] = ctypes.open(lib[l]);
}

//start mactypes
var Boolean = ctypes.unsigned_char;
var UniChar = ctypes.jschar;   // uint16 with automatic conversion
//end mactypes

//start CoreFoundationTypes
var CFTypeRef = ctypes.void_t.ptr;
var __CFString = new ctypes.StructType('__CFString');
var CFStringRef = __CFString.ptr;
var __CFAllocator = new ctypes.StructType('__CFAllocator');
var CFAllocatorRef = __CFAllocator.ptr;
var CFIndex = ctypes.long;
var CFRange = new ctypes.StructType('CFRange', [{location: CFIndex}, {length: CFIndex}]);
//end CoreFoundationTypes

//dictionary functionality
var __CFDictionary = new ctypes.StructType('__CFDictionary');
var CFDictionaryRef = __CFDictionary.ptr;
var CFDictionaryGetValue = lib.CoreFoundation.declare('CFDictionaryGetValue', ctypes.default_abi, ctypes.void_t.ptr/*returns CFTypeRef*/, CFDictionaryRef, ctypes.void_t.ptr/*CFStringRef*/);
//end dictionary functionality

//string functionality
var CFStringCreateWithCharacters = lib.CoreFoundation.declare('CFStringCreateWithCharacters', ctypes.default_abi, CFStringRef, CFAllocatorRef, UniChar.ptr, CFIndex);
var CFStringGetLength = lib.CoreFoundation.declare('CFStringGetLength', ctypes.default_abi, CFIndex, CFStringRef);
var CFStringGetCharacters = lib.CoreFoundation.declare('CFStringGetCharacters', ctypes.default_abi, ctypes.void_t, CFStringRef, CFRange, UniChar.ptr);
//end string functionality

//common declares
var CFRelease = lib.CoreFoundation.declare('CFRelease', ctypes.default_abi, ctypes.void_t, CFTypeRef);

function convertCFString(CFStr) { //CFStr is something like that is returned by `CFStringCreateWithCharacters` see: https://github.com/philikon/osxtypes/blob/b359c655b39e947d308163994f7cce94ca14d98f/README.txt#L20
    //start from: https://github.com/philikon/osxtypes/blob/b359c655b39e947d308163994f7cce94ca14d98f/README.txt#L22
    var length = CFStringGetLength(CFStr);
    var chars = ctypes.jschar.array(length)()
    CFStringGetCharacters(CFStr, CFRange(0, length), chars);
    var back = chars.readString();
    //end from: //start from: https://github.com/philikon/osxtypes/blob/b359c655b39e947d308163994f7cce94ca14d98f/README.txt#L22
    return back;
}

function makeCFStr(input) { //input is just a js string so like `var input = 'blah';`
    return CFStringCreateWithCharacters(null, input, input.length); //see: https://github.com/philikon/osxtypes/blob/b359c655b39e947d308163994f7cce94ca14d98f/README.txt#L20
}
//end common declares

var CGSessionCopyCurrentDictionary = lib.CoreGraphics.declare('CGSessionCopyCurrentDictionary', ctypes.default_abi, CFDictionaryRef);

var CGSessionDict = CGSessionCopyCurrentDictionary();
console.log(uneval(CGSessionDict));

var kCGSSessionOnConsoleKey_str = 'kCGSSessionOnConsoleKey';
var kCGSSessionOnConsoleKey = CFStringCreateWithCharacters(null, kCGSSessionOnConsoleKey_str, kCGSSessionOnConsoleKey_str.length); //works // i figured it should be a string because of: https://github.com/JuliaEichler/Mac_OSX_SDKs/blob/392649d7112884481a94b8cd1f601f3a5edae999/MacOSX10.6.sdk/System/Library/Frameworks/ApplicationServices.framework/Versions/A/Frameworks/CoreGraphics.framework/Versions/A/Headers/CGSession.h#L38 here they are making CFSTR of a text string

var kCGSSessionOnConsoleKey_val = CFDictionaryGetValue(CGSessionDict, kCGSSessionOnConsoleKey);
console.log('kCGSSessionOnConsoleKey_val:', kCGSSessionOnConsoleKey_val, uneval(kCGSSessionOnConsoleKey_val)); //printing `"kCGSSessionOnConsoleKey_val:" CData {  } "ctypes.voidptr_t(ctypes.UInt64("0x7fff7a13b7f0"))"`
if (kCGSSessionOnConsoleKey_val.isNull()) {
    console.log('CFDictionaryGetValue isNull so the key is not present in the dictionary, I am guesing');
} else {
    //read value
    var kCGSSessionOnConsoleKey_val_str = convertCFString(kCGSSessionOnConsoleKey_val); //throwing `Exception: expected type pointer, got ctypes.voidptr_t(ctypes.UInt64("0x7fff7a13b7f0"))`
}
CFRelease(kCGSSessionOnConsoleKey); //do release on things made with CFStringCreateWithCharacters per https://github.com/philikon/osxtypes/blob/master/examples/content/iphoto.js#L89

for (var l in lib) {
  lib[l].close();
}
因此,基本上在这个
convertCFString
中有一个函数
CFStringGetLength
,它接受
CFStringRef
的第一个参数,该参数被定义为
新的ctypes.void\u t.ptr
。我在
CFDictionaryGetValue
的返回值上运行这个函数,这个函数的返回值也是
ctypes.void\u t.ptr
,它前面没有一个
new

下面是
convertCFString
(从而
CFStringGetLength
)工作的示例:

我试过这样铸造它:

var casted = ctypes.cast(kCGSSessionOnConsoleKey_val, CFStringRef.ptr).contents;

这使得它看起来非常像
\uucfstring.ptr(ctypes.UInt64(“0x7fff7a13b7f0”)
,但当我在上面执行
转换CFString
时,它会使firefox崩溃。

弄明白了,我选错了。它也是一个布尔值,所以我必须将其转换为CFBooleanRef:

var casted = ctypes.cast(kCGSSessionOnConsoleKey_val, CFBooleanRef);
解决方案如下:

var casted = ctypes.cast(kCGSSessionOnConsoleKey_val, CFBooleanRef);