void KprWiFiInterfaceCallback(UInt16 state, UInt32 ip, unsigned char* mac) { if ((state == kprNetInterfaceConnected) && ip) { ip = FskEndianU32_BtoN(ip); KprNetworkInterfaceMark(ip, "wlan0"); if (mac) { int length = FskStrLen(mac); FskDebugStr("INTERFACE MAC = '%s' %d", mac, length); if (length == 17) { // 38:AA:3C:7B:02:9F unsigned char MAC[6] = { 0, 0, 0, 0, 0, 0 }; int i, j; for (i = length - 1, j = 0; j < 6; j++, i--) { unsigned char hex = mac[i--]; MAC[j] = ((hex > 0x40) ? hex - 7 : hex) & 0xf; hex = mac[i--]; MAC[j] |= (((hex > 0x40) ? hex - 7 : hex) & 0xf) << 4; } FskDebugStr("-> INTERFACE MAC = %2X:%2X:%2X:%2X:%2X:%2X", MAC[5], MAC[4], MAC[3], MAC[2], MAC[1], MAC[0]); } FskMemPtrDispose(mac); } } KprNetworkInterfaceSweep(); return kFskErrNone; }
static Boolean KprWebSocketEndpointValidateResponse(KprWebSocketEndpoint self, FskHeaders *response) { FskErr err; char *value; char *encoded = NULL; Boolean result = false; { FskHeaderIterator iter = FskHeaderIteratorNew(response); FskDebugStr("HANDSHAKE: response headers\n"); while (iter) { FskDebugStr("> %s: %s\n", iter->name, iter->value); iter = FskHeaderIteratorNext(iter); } FskHeaderIteratorDispose(iter); } if (response->responseCode != 101) return false; if (!KprWebSocketEndpointCheckHeaderValue(response, "Upgrade", "websocket")) return false; if (!KprWebSocketEndpointCheckHeaderValue(response, "Connection", "Upgrade")) return false; value = FskHeaderFind("Sec-WebSocket-Accept", response); if (!value) return false; bailIfError(KprWebSocketCalculateHash(self->key, &encoded)); result = (FskStrCompare(value, encoded) == 0); bail: if (encoded) FskMemPtrDispose(encoded); return result; }
static FskErr KprWebSocketEndpointConnectCallback(FskSocket skt, void *refCon) { FskErr err = kFskErrNone; KprWebSocketEndpoint self = refCon; FskDebugStr("CONNECT: callback was called\n"); if (!skt || 0 == skt->ipaddrRemote) { bailIfError(kFskErrSocketNotConnected); } bailIfError(KprWebSocketEndpointSetupSocketReader(self, skt, kKprWebSocketEndpoint_onHeader)); self->doMask = true; self->needNonMaskedFrame = true; if (self->cancelConnection) { KprWebSocketEndpointDisconnect(self); } else { bailIfError(KprWebSocketEndpointUpgradeConnection(self)); } bail: if (err) { CALLBACK(errorCallback)(self, err, "cannot start handshake", self->refcon); } return err; }
FskErr KprWebSocketEndpointClose(KprWebSocketEndpoint self, UInt16 code, char *reason) { FskErr err = kFskErrNone; FskDebugStr("CLOSE: (%d), %s\n", code, reason); self->closeCode = code; if (reason) { FskMemPtrDispose(self->closeReason); self->closeReason = FskStrDoCopy(reason); } switch (self->state) { case kKprWebSocketStateConnecting: bailIfError(KprWebSocketEndpointCancelConnection(self)); break; case kKprWebSocketStateOpen: bailIfError(KprWebSocketEndpointStartClosingHandshake(self, code, reason)); break; case kKprWebSocketStateClosing: case kKprWebSocketStateClosed: default: break; } bail: return err; }
void KprZeroconfPlatformCallBack(FskThreadDataHandler handler, FskThreadDataSource source, void* context) #endif { DNSServiceRef serviceRef = context; DNSServiceErrorType error = kDNSServiceErr_NoError; error = DNSServiceProcessResult(serviceRef); if (error) FskDebugStr("!!! KprZeroconfPlatformCallBack error %d", error); }
void KprNetworkInterfaceRemove(int ip) { char ipString[16]; char buffer[64]; KprMessage message = NULL; FskNetIPandPortToString(ip, 0, ipString); FskDebugStr("ADD INTERFACE %s", ipString); sprintf(buffer, "xkpr:///network/interface/remove?ip=%s", ipString); KprMessageNew(&message, buffer); if (message) KprMessageNotify(message); }
FskErr KprCoAPClientRequestDispose(KprCoAPClientRequest self) { FskErr err = kFskErrNone; if (self) { FskDebugStr("CoAP ClientRequest Disposed: %x", (int) self); KprCoAPMessageDispose(self->message); KprCoAPEndpointDispose(self->endpoint); KprMemPtrDispose(self); } return err; }
void KprWebSocketEndpointDispose(KprWebSocketEndpoint self) { if (self) { FskDebugStr("DISPOSE: KprWebSocketEndpoint\n"); if (self->socket) KprWebSocketEndpointDisconnect(self); if (self->url) FskMemPtrDispose(self->url); if (self->key) FskMemPtrDispose(self->key); if (self->origin) FskMemPtrDispose(self->origin); if (self->closeReason) FskMemPtrDispose(self->closeReason); if (self->parts) FskStrParsedUrlDispose(self->parts); FskInstrumentedItemDispose(self); FskMemPtrDispose(self); } }
FskErr FskECMAScriptInitializationComplete(void) { FskErr err = kFskErrNone; #if TARGET_OS_IPHONE FskCocoaApplicationRunLoopAddCallback(); #elif TARGET_OS_ANDROID { int useGL = 0; // let Android override "useGL" if (gAndroidCallbacks->getModelInfoCB) { gAndroidCallbacks->getModelInfoCB(NULL, NULL, NULL, NULL, &useGL); FskDebugStr("useGL: %d", useGL); FskEnvironmentSet("useGL", useGL ? "1" : "0"); } } #endif return err; }
FskErr KprCoAPServerSessionDispose(KprCoAPServerSession self) { FskErr err = kFskErrNone; if (self && KprRetainableRelease(self->retainable)) { FskDebugStr("CoAP ServerSession Disposed: %p", self); KprCoAPMessageDispose(self->request); KprCoAPMessageDispose(self->lastResponse); KprCoAPEndpointDispose(self->endpoint); KprRetainableDispose(self->retainable); KprMemPtrDispose(self); } return err; }
void KprServicesStart(KprShell shell) { UInt32 flags = kFskThreadFlagsWaitForInit | kFskThreadFlagsJoinable; KprService service = gServices; FskThread thread = KprShellGetThread(gShell); xsMachine* the = gShell->the; gServicesThreadQuitting = false; FskThreadCreate(&gServicesThread, KprServicesLoop, flags, NULL, "services"); while (service) { if (!(service->flags & kprServicesThread)) { FskDebugStr("Starting %s", service->id); (*service->start)(service, thread, the); } service = service->next; } }
FskErr KprWebSocketEndpointNew(KprWebSocketEndpoint* it, void *refcon) { FskErr err = kFskErrNone; KprWebSocketEndpoint self = NULL; bailIfError(FskMemPtrNewClear(sizeof(KprWebSocketEndpointRecord), it)); self = *it; FskInstrumentedItemNew(self, NULL, &gKprWebSocketEndpointInstrumentation); self->refcon = refcon; self->state = kKprWebSocketStateConnecting; FskDebugStr("CREATE: KprWebSocketEndpoint\n"); return err; bail: if (self) KprWebSocketEndpointDispose(self); return err; }
static void KprWebSocketEndpointStartConnect(KprWebSocketEndpoint self) { FskErr err = kFskErrNone; int port = 80; long flags = 0; if (self->parts->port) port = self->parts->port; if (self->isSecure) { if (port == 80) port = 443; flags |= kConnectFlagsSSLConnection; } bailIfError(FskNetConnectToHost(self->parts->host, port, false, KprWebSocketEndpointConnectCallback, self, flags, NULL, "WebSocket")); bail: if (err) { FskDebugStr("ERROR: %d\n", err); CALLBACK(errorCallback)(self, err, "cannot start connection", self->refcon); } }
static FskErr KprWebSocketEndpointHandleResponse(KprWebSocketEndpoint self, FskHeaders *response) { FskErr err = kFskErrNone; if (self->cancelConnection) { KprWebSocketEndpointDisconnect(self); return err; } if (!KprWebSocketEndpointValidateResponse(self, response)) { KprWebSocketEndpointDisconnect(self); return -1; } FskDebugStr("HANDSHAKE: done. upgraded to websocket\n"); self->state = kKprWebSocketStateOpen; CALLBACK(openCallback)(self, self->refcon); return kFskErrNone; }
static void KprMQTTClientIdle(FskTimeCallBack callback UNUSED, const FskTime time, void *it) { KprMQTTClient self = it; FskErr err; KprMQTTMessage message = NULL; FskTimeRecord when; bailIfError(KprMQTTMessageNewWithType(&message, kKprMQTTMessageTypePINGREQ)); bailIfError(KprMQTTClientSendMessage(self, &message)); when = *time; FskDebugStr("< PING %ld", when.seconds); FskTimeAddSecs(&when, self->keepAlive); FskTimeCallbackSet(self->pingResponseCallaback, &when, KprMQTTClientCheckPingResponse, self); bail: if (err) { KprMQTTClientHandleError(self, err, "sending ping"); } KprMQTTMessageDispose(message); }
FskErr KprCoAPClientDispose(KprCoAPClient self) { FskErr err = kFskErrNone; if (self) { KprCoAPClientResolver resolver; KprCoAPClientRequest request; KprCoAPEndpoint endpoint; resolver = self->resolvers; while (resolver) { KprCoAPClientResolver next = resolver->next; KprCoAPClientResolverDispose(resolver); resolver = next; } request = self->requests; while (request) { KprCoAPClientRequest next = request->next; KprCoAPClientRequestDispose(request); request = next; } endpoint = self->endpoints; while (endpoint) { KprCoAPEndpoint next = endpoint->next; KprCoAPEndpointDispose(endpoint); endpoint = next; } KprMemoryBlockDispose(self->recycleTokens); KprCoAPReceiverDispose(self->receiver); FskNetSocketClose(self->socket); KprMemPtrDispose(self); FskDebugStr("CoAP Client disposed: %p", self); } return err; }
FskErr KprCoAPClientNew(KprCoAPClient *it, KprCoAPClientCallbacks *callbacks, void *refcon) { FskErr err = kFskErrNone; KprCoAPClient self = NULL; FskSocket socket = NULL; KprCoAPReceiver receiver = NULL; KprCoAPReceiverCallbacks receiverCallback = { KprCoAPClient_receiveCallback, KprCoAPClient_errorCallback, }; bailIfError(KprMemPtrNewClear(sizeof(KprCoAPClientRecord), &self)); bailIfError(FskNetSocketNewUDP(&socket, "KprCoAPClient")); bailIfError(FskNetSocketBind(socket, -1, 0)); bailIfError(KprCoAPReceiverNew(&receiver, socket, &receiverCallback, self)); self->socket = socket; self->receiver = receiver; self->messageId = FskRandom(); self->autoToken = false; self->nextTokenBytes = 1; self->callbacks = *callbacks; self->refcon = refcon; *it = self; FskDebugStr("CoAP Client created: %p", self); bail: if (err) { FskNetSocketClose(socket); KprCoAPReceiverDispose(receiver); KprCoAPClientDispose(self); } return err; }
static FskErr KprWebSocketEndpointHandleFrame(KprWebSocketEndpoint self, UInt8 opcode, UInt8 *message, UInt32 length) { FskErr err = kFskErrNone; if (self->closeWasReceived) return kFskErrConnectionClosed; switch (opcode) { case kKprWebSocketOpcodeTextFrame: if (!self->ignoreFurtherFrame) { FskDebugStr("FRAME: Text! (%ld bytes)\n", length); err = KprWebSocketEndpointHandleTextMessage(self, message, length); } break; case kKprWebSocketOpcodeBinaryFrame: if (!self->ignoreFurtherFrame) { FskDebugStr("FRAME: Binary! (%ld bytes)\n", length); err = KprWebSocketEndpointHandleBinaryMessage(self, message, length); } break; case kKprWebSocketOpcodeClose: FskDebugStr("FRAME: Close!\n"); err = KprWebSocketEndpointHandleCloseFrame(self, message, length); break; case kKprWebSocketOpcodePing: if (!self->ignoreFurtherFrame) { FskDebugStr("FRAME: Ping!\n"); bailIfError(KprWebSocketEndpointSendRawFrame(self, kKprWebSocketOpcodePong, message, length)); } break; case kKprWebSocketOpcodePong: FskDebugStr("FRAME: Pong!\n"); break; default: FskDebugStr("FRAME: Unknown opcode %d! (%ld bytes)\n", (int) opcode, length); break; } bail: return err; }
static void KprServicesLoop(void* theParameter) { xsAllocation allocation = { 1100000, // 700 * 1024, 32 * 1024, 70000, // 62000, 4096, 2048, 16000, 1993 }; FskErr err = kFskErrNone; KprService service = gServices; FskThread thread = FskThreadGetCurrent(); xsMachine* the = xsAliasMachine(&allocation, gShell->root, "services", gShell); bailIfNULL(the); while (service) { if (service->flags & kprServicesThread) { FskDebugStr("Starting %s", service->id); (*service->start)(service, thread, the); } service = service->next; } FskThreadInitializationComplete(thread); while (!gServicesThreadQuitting) FskThreadRunloopCycle(-1); service = gServices; while (service) { if (service->flags & kprServicesThread) (*service->stop)(service); service = service->next; } bail: if (the) xsDeleteMachine(the); return; }
FskErr KprCoAPClientRequestNew(KprCoAPClientRequest *it, KprCoAPClient client, KprCoAPMessage message, KprCoAPEndpoint endpoint) { FskErr err = kFskErrNone; KprCoAPClientRequest self = NULL; KprCoAPMessageOptionRecord *option; bailIfError(KprMemPtrNewClear(sizeof(KprCoAPClientRequestRecord), &self)); self->client = client; self->message= KprRetain(message); self->endpoint = KprRetain(endpoint); option = KprCoAPMessageFindOption(message, kKprCoAPMessageOptionObserve); self->observeRequested = (option != NULL && option->value.uint == kKprCoAPMessageObserveRegister); *it = self; FskDebugStr("CoAP ClientRequest created: %x", (int) self); bail: if (err) { KprCoAPClientRequestDispose(self); } return err; }
FskErr FskECMAScriptLoadLibrary(const char *name) { FskErr err = kFskErrBadData; FskLibraryLoadProc libLoad; char *extension = NULL, *symbolName = NULL, *dot, *slash, *fullPath = NULL, *temp = NULL; FskLibrary library = NULL; char* root = NULL; FskFileInfo itemInfo; FskDebugStr("FskECMAScriptLoadLibrary: %s", name); dot = FskStrRChr(name, '.'); slash = FskStrRChr(name, '/'); if ((NULL == dot) || (slash && (slash > dot))) { #if TARGET_OS_WIN32 extension = ".dll"; #elif TARGET_OS_MAC || TARGET_OS_LINUX extension = ".so"; #elif TARGET_OS_KPL extension = (char*)KplECMAScriptGetExtension(); #endif } if (extension) fullPath = FskStrDoCat(name, extension); else fullPath = FskStrDoCopy(name); if (kFskErrNone != FskFileGetFileInfo(fullPath, &itemInfo)) { #if TARGET_OS_ANDROID char *libDir; libDir = FskStrDoCat(gAndroidCallbacks->getStaticDataDirCB(), "../lib/lib"); temp = FskStrDoCat(libDir, fullPath); FskMemPtrDispose(libDir); #else root = FskGetApplicationPath(); temp = FskStrDoCat(root, fullPath); FskMemPtrDispose(root); #endif if (kFskErrNone != FskFileGetFileInfo(temp, &itemInfo)) { FskDebugStr(" - no file: %s", temp); goto bail; } FskMemPtrDispose(fullPath); fullPath = temp; temp = NULL; } err = FskLibraryLoad(&library, fullPath); FskDebugStr(" - try: %s -> %d", fullPath, err); if (err) goto bail; symbolName = FskStrDoCat(name, "_fskLoad"); if ((kFskErrNone == FskLibraryGetSymbolAddress(library, symbolName, &libLoad)) || (kFskErrNone == FskLibraryGetSymbolAddress(library, "fskLoad", &libLoad))) { err = (libLoad)(library); FskDebugStr(" - symbolName: %x -> %d", libLoad, err); if (err) goto bail; err = kFskErrNone; } bail: if (err) { FskLibraryUnload(library); } FskMemPtrDispose(symbolName); FskMemPtrDispose(fullPath); return err; }
void KprDebugMachineWriteError(KprSocketErrorContext context UNUSED, FskErr err, void *refcon) { // KprDebugMachine self = refcon; FskDebugStr("write error"); return; }
FskErr FskTextFreeTypeInstallFonts(char* fontsPath, char* defaultFont) { FskErr err = kFskErrNone; FskTextEngine fte; char *fromDirectory = NULL; char* fromPath = NULL; FskDirectoryIterator iterator = NULL; char *name = NULL; UInt32 type; #if TARGET_OS_ANDROID char *toDirectory = NULL; char* toPath = NULL; FskFileInfo itemInfo; FskFileMapping map = NULL; unsigned char *data; FskInt64 dataSize; FskFile file = NULL; #endif err = FskTextEngineNew(&fte, NULL); if (err) goto bail; fromDirectory = FskEnvironmentDoApply(FskStrDoCopy(fontsPath)); if (!fromDirectory) { err = kFskErrMemFull; goto bail; } #if TARGET_OS_ANDROID if (!FskStrCompareWithLength(fromDirectory, "/data/app/", 10)) { err = FskDirectoryGetSpecialPath(kFskDirectorySpecialTypeApplicationPreference, false, NULL, &toDirectory); if (err) goto bail; } #endif err = FskDirectoryIteratorNew(fromDirectory, &iterator, 0); if (err) goto bail; while (kFskErrNone == FskDirectoryIteratorGetNext(iterator, &name, &type)) { if (type == kFskDirectoryItemIsFile) { fromPath = FskStrDoCat(fromDirectory, name); if (!fromPath) { err = kFskErrMemFull; goto bail; } FskDebugStr("from %s", fromPath); #if TARGET_OS_ANDROID if (toDirectory) { toPath = FskStrDoCat(toDirectory, name); FskDebugStr("to %s", toPath); if (kFskErrNone != FskFileGetFileInfo(toPath, &itemInfo)) { err = FskFileMap(fromPath, &data, &dataSize, 0, &map); if (err) goto bail; err = FskFileCreate(toPath); if (err) goto bail; err = FskFileOpen(toPath, kFskFilePermissionReadWrite, &file); if (err) goto bail; err = FskFileWrite(file, dataSize, data, NULL); if (err) goto bail; FskFileClose(file); file = NULL; FskFileDisposeMap(map); map = NULL; } FskDebugStr("add %s", toPath); FskTextAddFontFile(fte, toPath); FskMemPtrDisposeAt(&toPath); } else #endif FskTextAddFontFile(fte, fromPath); FskMemPtrDisposeAt(&fromPath); } FskMemPtrDisposeAt(&name); } #if TARGET_OS_ANDROID if (gAndroidCallbacks->getModelInfoCB) { char* osVersion; gAndroidCallbacks->getModelInfoCB(NULL, &osVersion, NULL, NULL, NULL); if ((FskStrStr(osVersion, "android.5") == osVersion) // for KPR applications || (FskStrStr(osVersion, "5.") == osVersion)) { // for tests BAIL_IF_ERR(err = FskFTAddMapping("/system/etc/fonts.xml")); } if ((FskStrStr(osVersion, "android.4") == osVersion) // for KPR applications || (FskStrStr(osVersion, "4.") == osVersion)) { // for tests BAIL_IF_ERR(err = FskFTAddMapping("/system/etc/system_fonts.xml")); err = FskFTAddMapping("/vendor/etc/fallback_fonts.xml"); if (err != kFskErrFileNotFound) BAIL(err); BAIL_IF_ERR(err = FskFTAddMapping("/system/etc/fallback_fonts.xml")); } else { defaultFont = "Droid Sans"; BAIL_IF_ERR(err = FskFTAddMapping(NULL)); } } #endif if (defaultFont) FskTextDefaultFontSet(fte, defaultFont); bail: #if TARGET_OS_ANDROID if (file) FskFileClose(file); if (map) FskFileDisposeMap(map); FskMemPtrDispose(toPath); FskMemPtrDispose(toDirectory); #endif FskMemPtrDispose(name); FskDirectoryIteratorDispose(iterator); FskMemPtrDispose(fromPath); FskMemPtrDispose(fromDirectory); FskTextEngineDispose(fte); return err; }