int prFilePutFloatLE(struct VMGlobals *g, int numArgsPushed) { PyrSlot *a, *b; PyrFile *pfile; FILE *file; a = g->sp - 1; b = g->sp; pfile = (PyrFile*)slotRawObject(a); file = (FILE*)slotRawPtr(&pfile->fileptr); if (file == NULL) { dumpObjectSlot(a); return errFailed; } float val; int err = slotFloatVal(b, &val); if (err) return err; SC_IOStream<FILE*> scio(file); scio.writeFloat_le(val); return errNone; }
int prLID_GetAbsInfo(VMGlobals *g, int numArgsPushed) { PyrSlot* args = g->sp - 2; int evtCode; int err; PyrObject* obj = SC_LID::getObject(args+0); if (!obj) return errWrongType; err = slotIntVal(args+1, &evtCode); if (err) return err; if (!isKindOfSlot(args+2, s_absInfoClass->u.classobj)) return errWrongType; PyrObject* infoObj = slotRawObject(&args[2]); SC_LID* dev = SC_LID::getDevice(obj); if (!dev) return errFailed; struct input_absinfo info; err = dev->getAbsInfo(evtCode, &info); if (err) return err; SetInt(infoObj->slots+0, info.value); SetInt(infoObj->slots+1, info.minimum); SetInt(infoObj->slots+2, info.maximum); SetInt(infoObj->slots+3, info.fuzz); SetInt(infoObj->slots+4, info.flat); slotCopy(&args[0], &args[2]); return errNone; }
int makeSynthBundle(big_scpacket *packet, PyrSlot *slots, int size, bool useElapsed) { double time; int err; int64 oscTime; err = slotDoubleVal(slots, &time); if (!err) { if (useElapsed) { oscTime = ElapsedTimeToOSC(time); } else { oscTime = (int64)(time * kSecondsToOSC); } } else { oscTime = 1; // immediate } packet->OpenBundle(oscTime); for (int i=1; i<size; ++i) { if (isKindOfSlot(slots+i, class_array)) { PyrObject *obj = slotRawObject(&slots[i]); int error = makeSynthMsgWithTags(packet, obj->slots, obj->size); if (error != errNone) return error; } } packet->CloseBundle(); return errNone; }
int prArray_OSCBytes(VMGlobals *g, int numArgsPushed) { PyrSlot* a = g->sp; PyrObject *array = slotRawObject(a); PyrSlot* args = array->slots; int numargs = array->size; if (numargs < 1) return errFailed; big_scpacket packet; if (IsFloat(args) || IsNil(args) || IsInt(args)) { makeSynthBundle(&packet, args, numargs, false); } else if (IsSym(args) || isKindOfSlot(args, class_string)) { int error = makeSynthMsgWithTags(&packet, args, numargs); if (error != errNone) return error; } else { return errWrongType; } int size = packet.size(); PyrInt8Array* obj = newPyrInt8Array(g->gc, size, 0, true); obj->size = size; memcpy(obj->b, packet.data(), size); SetObject(a, (PyrObject*)obj); //for (int i=0; i<packet.size()/4; i++) post("%d %p\n", i, packet.buf[i]); return errNone; }
int prConnectSharedMem(VMGlobals *g, int numArgsPushed) { #if !defined(SC_IPHONE) PyrSlot *a = g->sp - 1; PyrSlot *b = g->sp; assert(IsObj(a)); PyrObject * self = slotRawObject(a); int portNumber = slotRawInt(b); int ptrIndex = 0; int finalizerIndex = 1; try { server_shared_memory_client * client = new server_shared_memory_client(portNumber); SetPtr(self->slots + ptrIndex, client); InstallFinalizer(g, self, finalizerIndex, disconnectSharedMem); postfl("Shared memory server interface initialized\n"); } catch (std::exception & e) { postfl("Cannot connect to shared memory: %s\n", e.what()); return errFailed; } #else postfl("Warning: Shared memory server interface disabled on iphone\n"); #endif return errNone; }
int prSetControlBusValue(VMGlobals *g, int numArgsPushed) { PyrSlot *a = g->sp - 2; PyrSlot *b = g->sp - 1; PyrSlot *c = g->sp; assert(IsObj(a)); PyrObject * self = slotRawObject(a); int ptrIndex = 0; PyrSlot * ptrSlot = self->slots + ptrIndex; if (NotPtr(ptrSlot)) return errFailed; if (!IsInt(b)) return errFailed; int busIndex = slotRawInt(b); if (NotPtr(ptrSlot)) return errFailed; float value; int error = slotFloatVal(c, &value); if (error != errNone) return error; server_shared_memory_client * client = (server_shared_memory_client*)slotRawPtr(ptrSlot); client->get_control_busses()[busIndex] = value; return errNone; }
int prPriorityQueueClear(struct VMGlobals *g, int numArgsPushed) { PyrSlot* a = g->sp; // priority queue PriorityQueueClear(slotRawObject(a)); return errNone; }
int prSignalAddHarmonic(struct VMGlobals *g, int numArgsPushed) { PyrSlot *a, *b, *c, *d; int err; float harmonic, amp; double phase, step; PyrObject *signal; float *out; a = g->sp - 3; b = g->sp - 2; c = g->sp - 1; d = g->sp; err = slotFloatVal(b, &harmonic); if (err) return errWrongType; err = slotFloatVal(c, &); if (err) return errWrongType; err = slotDoubleVal(d, &phase); if (err) return errWrongType; signal = slotRawObject(a); out = (float*)(signal->slots) - 1; step = twopi * harmonic / signal->size; UNROLL_CODE(signal->size, out, *++out += sin(phase) * amp; phase += step; );
void PriorityQueueAdd(struct VMGlobals *g, PyrObject* queueobj, PyrSlot* item, double time) { PyrObject *schedq, *newschedq; int size, maxsize; PyrSlot *schedqSlot = queueobj->slots; if (!IsObj(schedqSlot)) { size = 32; schedq = newPyrArray(g->gc, size, 0, true); schedq->size = 1; SetInt(schedq->slots + 0, 0); // stability count SetObject(schedqSlot, schedq); g->gc->GCWrite(queueobj, schedq); } else { schedq = slotRawObject(schedqSlot); maxsize = ARRAYMAXINDEXSIZE(schedq); size = schedq->size; if (size+3 > maxsize) { newschedq = newPyrArray(g->gc, maxsize*2, 0, true); newschedq->size = size; slotCopy(newschedq->slots, schedq->slots, size); assert(IsInt(newschedq->slots)); SetObject(schedqSlot, newschedq); g->gc->GCWrite(queueobj, newschedq); schedq = newschedq; } } addheap(g, schedq, time, item); }
static QObjectProxy* read( PyrSlot *slot ) { PyrSlot *proxySlot = slotRawObject( slot )->slots; if( IsPtr( proxySlot ) ) return (QObjectProxy*) slotRawPtr( proxySlot ); else return 0; }
int prArrayMultiChanExpand(struct VMGlobals *g, int numArgsPushed) { PyrSlot *a, *slot, *slots1, *slots2, *slots3, *slots4; PyrObject *obj1, *obj2, *obj3, *obj4; int i, j, size, len, maxlen; a = g->sp; obj1 = slotRawObject(a); size = obj1->size; slots1 = obj1->slots; maxlen = 1; for (j=0; j<size; ++j) { slot = slots1 + j; if (IsObj(slot)) { if (slotRawObject(slot)->classptr == class_array) { len = slotRawObject(slot)->size; maxlen = len > maxlen ? len : maxlen; } else if (isKindOf(slotRawObject(slot), class_sequenceable_collection) && (slotRawObject(slot)->classptr != class_string)) { return errFailed; // this primitive only handles Arrays. } } } obj2 = newPyrArray(g->gc, maxlen, 0, true); SetObject(a, obj2); slots2 = obj2->slots; for (i=0; i<maxlen; ++i) { obj3 = newPyrArray(g->gc, size, 0, true); obj3->size = size; SetObject(slots2 + i, obj3); g->gc->GCWriteNew(obj2, obj3); // we know obj3 is white so we can use GCWriteNew obj2->size++; slots1 = obj1->slots; slots3 = obj3->slots; for (j=0; j<size; ++j) { slot = slots1 + j; if (IsObj(slot)) { if (slotRawObject(slot)->classptr == class_array && slotRawObject(slot)->size > 0) { PyrSlot *slotToCopy; obj4 = slotRawObject(slot); slots4 = obj4->slots; slotToCopy = &slots4[i % obj4->size]; slotCopy(&slots3[j],slotToCopy); g->gc->GCWrite(obj3, slotToCopy); } else { slotCopy(&slots3[j],slot); g->gc->GCWrite(obj3, slot); } } else { slotCopy(&slots3[j],slot); // we don't need GCWrite here, as slot is not an object } } } return errNone; }
int prTempoClock_Dump(struct VMGlobals *g, int numArgsPushed) { PyrSlot *a = g->sp; TempoClock *clock = (TempoClock*)slotRawPtr(&slotRawObject(a)->slots[1]); if (clock) clock->Dump(); return errNone; }
int prDisconnectSharedMem(VMGlobals *g, int numArgsPushed) { PyrSlot *a = g->sp; assert(IsObj(a)); PyrObject * self = slotRawObject(a); return disconnectSharedMem(g, self); }
int prNetAddr_SendRaw(VMGlobals *g, int numArgsPushed) { PyrSlot* netAddrSlot = g->sp - 1; PyrSlot* arraySlot = g->sp; PyrObject* netAddrObj = slotRawObject(netAddrSlot); if (!IsObj(arraySlot) || !isKindOf(slotRawObject(arraySlot), class_rawarray)) { error("sendRaw arg must be a kind of RawArray.\n"); return errWrongType; } PyrObject *array = slotRawObject(arraySlot); char *bufptr = (char*)array->slots; int32 msglen = array->size * gFormatElemSize[array->obj_format]; return netAddrSend(netAddrObj, msglen, bufptr, false); }
inline int prOpFloat(VMGlobals *g, int numArgsPushed) { PyrSlot *a, *b; PyrSymbol *msg; a = g->sp - 1; b = g->sp; switch (GetTag(b)) { case tagInt : SetRaw(a, Functor::run(slotRawFloat(a), (double)slotRawInt(b))); break; case tagChar : case tagPtr : case tagNil : case tagFalse : case tagTrue : goto send_normal_2; case tagSym : SetSymbol(a, slotRawSymbol(b)); break; case tagObj : if (isKindOf(slotRawObject(b), class_signal)) SetObject(a, Functor::signal_fx(g, slotRawFloat(a), slotRawObject(b))); else goto send_normal_2; break; default : SetRaw(a, Functor::run(slotRawFloat(a), slotRawFloat(b))); break; } g->sp-- ; // drop g->numpop = 0; #if TAILCALLOPTIMIZE g->tailCall = 0; #endif return errNone; send_normal_2: if (numArgsPushed != -1) // special case flag meaning it is a primitive return errFailed; // arguments remain on the stack msg = gSpecialBinarySelectors[g->primitiveIndex]; sendMessage(g, msg, 2); return errNone; }
int prSignalOverWrite(struct VMGlobals *g, int numArgsPushed) { PyrSlot *a, *b, *c; int err; int index; a = g->sp - 2; b = g->sp - 1; c = g->sp; if (NotObj(b) || !isKindOf(slotRawObject(b), class_signal)) return errWrongType; err = slotIntVal(c, &index); if (err) return errWrongType; signal_overwrite(g, slotRawObject(a), slotRawObject(b), index); return errNone; }
int prSFOpenRead(struct VMGlobals *g, int numArgsPushed) { PyrSlot *a, *b; char filename[PATH_MAX]; SNDFILE *file; SF_INFO info; const char *headerstr; const char *sampleformatstr; a = g->sp - 1; b = g->sp; PyrObject *obj1 = slotRawObject(a); if (!isKindOfSlot(b, class_string)) return errWrongType; if (slotRawObject(b)->size > PATH_MAX - 1) return errFailed; memcpy(filename, slotRawString(b)->s, slotRawObject(b)->size); filename[slotRawString(b)->size] = 0; info.format = 0; file = sf_open(filename, SFM_READ, &info); if (file) { SetPtr(obj1->slots + 0, file); sndfileFormatInfoToStrings(&info, &headerstr, &sampleformatstr); //headerFormatToString(&info, &headerstr); PyrString *hpstr = newPyrString(g->gc, headerstr, 0, true); SetObject(obj1->slots+1, hpstr); g->gc->GCWriteNew(obj1, (PyrObjectHdr*)hpstr); // we know hpstr is white so we can use GCWriteNew PyrString *smpstr = newPyrString(g->gc, sampleformatstr, 0, true); SetObject(obj1->slots+2, smpstr); g->gc->GCWriteNew(obj1, (PyrObjectHdr*)smpstr); // we know smpstr is white so we can use GCWriteNew SetInt(obj1->slots + 3, info.frames); SetInt(obj1->slots + 4, info.channels); SetInt(obj1->slots + 5, info.samplerate); SetTrue(a); } else { SetNil(a); SetFalse(a); } return errNone; }
int prPipeOpen(struct VMGlobals *g, int numArgsPushed) { PyrSlot *a, *b, *c; char mode[12]; PyrFile *pfile; FILE *file; a = g->sp - 2; b = g->sp - 1; c = g->sp; if (NotObj(c) || !isKindOf(slotRawObject(c), class_string) || NotObj(b) || !isKindOf(slotRawObject(b), class_string)) return errWrongType; if (slotRawObject(c)->size > 11) return errFailed; pfile = (PyrFile*)slotRawObject(a); char *commandLine = (char*)malloc(slotRawObject(b)->size + 1); memcpy(commandLine, slotRawString(b)->s, slotRawObject(b)->size); commandLine[slotRawString(b)->size] = 0; memcpy(mode, slotRawString(c)->s, slotRawObject(c)->size); mode[slotRawString(c)->size] = 0; pid_t pid; file = sc_popen(commandLine, &pid, mode); free(commandLine); if (file) { SetPtr(&pfile->fileptr, file); SetInt(a, pid); } else { SetNil(a); } return errNone; }
int prHID_API_Initialize(VMGlobals* g, int numArgsPushed) { PyrSlot *args = g->sp - numArgsPushed + 1; PyrSlot *self = args + 0; SC_HID_APIManager::instance().setPyrObject( slotRawObject(self) ); // initialize HID_APIManager return SC_HID_APIManager::instance().init(); }
int prSignalNormalizeTransferFn(struct VMGlobals *g, int numArgsPushed) { PyrSlot *a; a = g->sp; signal_normalize_transfer_fn(slotRawObject(a)); return errNone; }
int prSignalIntegral(struct VMGlobals *g, int numArgsPushed) { PyrSlot *a; a = g->sp; SetFloat(a, signal_integral(slotRawObject(a))); return errNone; }
bool PyrGC::BlackToWhiteCheck(PyrObject *objA) { if (objA->obj_format > obj_slot) return true; // scan it int size = objA->size; if (size > 0) { PyrSlot *slot = objA->slots; for (int j=size; j--; ++slot) { PyrObject * objB = NULL; if (IsObj(slot) && slotRawObject(slot)) { objB = slotRawObject(slot); } if (objB && (unsigned long)objB < 100) { fprintf(stderr, "weird obj ptr\n"); return false; } if (objB) { if (objA == mStack) continue; if (objA->gc_color == mBlackColor && objA != mPartialScanObj) { if (objB->gc_color == mWhiteColor) { if (objA->classptr == class_frame) { // jmc: black stack frames pointing to white nodes can be ignore PyrFrame * frameA = (PyrFrame*)objA; PyrMethod * meth = slotRawMethod(&frameA->method); PyrMethodRaw * methraw = METHRAW(meth); if (methraw->needsHeapContext) continue; } #if DUMPINSANITY fprintf(stderr, "black frame to white ref %p %p\n", objA, objB); dumpBadObject(objA); dumpBadObject(objB); fprintf(stderr, "\n"); #endif return false; } } } } } return true; }
int prFilePutString(struct VMGlobals *g, int numArgsPushed) { PyrSlot *a, *b; PyrFile *pfile; FILE *file; PyrString *string; a = g->sp - 1; b = g->sp; pfile = (PyrFile*)slotRawObject(a); file = (FILE*)slotRawPtr(&pfile->fileptr); if (file == NULL) return errFailed; if (NotObj(b) || slotRawObject(b)->classptr != class_string) return errWrongType; string = slotRawString(b); if (string->size) { fwrite(string->s, 1, string->size, file); } return errNone; }
static int prNetAddr_Disconnect(VMGlobals *g, int numArgsPushed) { PyrSlot* netAddrSlot = g->sp; PyrObject* netAddrObj = slotRawObject(netAddrSlot); SC_TcpClientPort *comPort = (SC_TcpClientPort*)slotRawPtr(netAddrObj->slots + ivxNetAddr_Socket); if (comPort) comPort->Close(); return errNone; }
void PriorityQueueClear(PyrObject *queueobj) { PyrSlot *schedqSlot = queueobj->slots; if (IsObj(schedqSlot)) { PyrObject *schedq = slotRawObject(schedqSlot); SetInt(schedq->slots, 0); // stability count schedq->size = 1; } }
static int addMsgSlot(big_scpacket *packet, PyrSlot *slot) { switch (GetTag(slot)) { case tagInt : packet->addi(slotRawInt(slot)); break; case tagSym : packet->adds(slotRawSymbol(slot)->name); break; case tagObj : if (isKindOf(slotRawObject(slot), class_string)) { PyrString *stringObj = slotRawString(slot); packet->adds(stringObj->s, stringObj->size); } else if (isKindOf(slotRawObject(slot), class_int8array)) { PyrInt8Array *arrayObj = slotRawInt8Array(slot); packet->addb(arrayObj->b, arrayObj->size); } else if (isKindOf(slotRawObject(slot), class_array)) { PyrObject *arrayObj = slotRawObject(slot); big_scpacket packet2; if (arrayObj->size > 1 && isKindOfSlot(arrayObj->slots+1, class_array)) { makeSynthBundle(&packet2, arrayObj->slots, arrayObj->size, true); } else { int error = makeSynthMsgWithTags(&packet2, arrayObj->slots, arrayObj->size); if (error != errNone) return error; } packet->addb((uint8*)packet2.data(), packet2.size()); } break; case tagNil : case tagTrue : case tagFalse : case tagChar : case tagPtr : break; default : if (gUseDoubles) packet->addd(slotRawFloat(slot)); else packet->addf(slotRawFloat(slot)); break; } return errNone; }
bool PyrGC::SanityMarkObj(PyrObject *objA, PyrObject *fromObj, int level) { if (objA->IsPermanent()) return true; if (objA->IsMarked()) return true; if (objA->size > MAXINDEXSIZE(objA)) { fprintf(stderr, "obj indexed size larger than max: %d > %ld\n", objA->size, MAXINDEXSIZE(objA)); //dumpObject((PyrObject*)objA); return false; } objA->SetMark(); // mark it if (!BlackToWhiteCheck(objA)) return false; if (objA->obj_format <= obj_slot) { // scan it int size = objA->size; if (size > 0) { PyrSlot *slot = objA->slots; for (int j=size; j--; ++slot) { PyrObject * objB = NULL; int tag = GetTag(slot); if (tag == tagObj && slotRawObject(slot)) objB = slotRawObject(slot); if (objB) { /* if (level > 40) { fprintf(stderr, "40 levels deep!\n"); dumpBadObject(objA); dumpBadObject(objB); return false; } */ bool err = SanityMarkObj(objB, objA, level + 1); if (!err) return false; } } } } return true; }
int prIdentDict_Put(struct VMGlobals *g, int numArgsPushed) { PyrSlot *a, *b, *c; a = g->sp - 2; // dict b = g->sp - 1; // key c = g->sp; // value if(IsNil(b)) return errWrongType; if(IsNil(c)) return errFailed; // will call removeAt return identDictPut(g, slotRawObject(a), b, c); }
void schedClearUnsafe() { //postfl("->schedClear %d\n", gRunSched); if (gRunSched) { VMGlobals *g = gMainVMGlobals; PyrObject* inQueue = slotRawObject(&g->process->sysSchedulerQueue); inQueue->size = 1; pthread_cond_signal (&gSchedCond); //pthread_mutex_unlock (&gLangMutex); } //postfl("<-schedClear %d\n", gRunSched); }
void PriorityQueuePostpone(PyrObject* queueobj, double time) { PyrSlot *schedqSlot = queueobj->slots; if (IsObj(schedqSlot)) { PyrObject *schedq = slotRawObject(schedqSlot); PyrSlot* slots = schedq->slots; for (int i=1; i < schedq->size; i+=3) { SetRaw(&slots[i], slotRawFloat(&slots[i]) + time); } } }