370 likes | 467 Views
ScriptBasic Segéd Modulok. Peter Verh á s 2002 március 5. Tartalom. Többszálú programozás Memória kezelő modul Változó kezelés Szimbólum tábla kezelés Naplózó modul, többszálú programozás. Többszálú programozás. Szálak, ( thread ) egyszerre futnak Közös memória terület
E N D
ScriptBasic Segéd Modulok Peter Verhás 2002 március 5.
Tartalom • Többszálú programozás • Memória kezelő modul • Változó kezelés • Szimbólum tábla kezelés • Naplózó modul, többszálú programozás
Többszálú programozás • Szálak, (thread) egyszerre futnak • Közös memória terület • Zárak, szemaforok • Processzek: külön memória terület • thread.c UNIX és NT közös implementáció
Miért kell a többszálú programozás? • Szerver több klienssel akiket egyszerre szolgál ki • Kiszolgálás közben vannak lassú, inaktív részek • Nagy számítás igényű feladat többprocesszoros gépen
Hogyan lehet egy szálat elindítani? int thread_CreateThread( PTHREADHANDLE pThread, void *pStartFunction, void *pThreadParameter ); • Visszatérési érték: hiba kód • Egyéb paraméterek
Mi a MUTEX? • Váltóbot • Pontosan egy valaki foghatja meg • Sorban lehet rá várni • MUTual EXclusive
Megosztott zár • Többen foghatják olvasásra • Csak egyvalaki foghatja meg írásra, és közben senki sem olvashatja • Sorban lehet várni rá • Házi feladat: hogyan kell megvalósítani megosztott zárat MUTEXekkel?
Körbevárás • Egy feladathoz két vagy több zár kell, A és B • P1 szál fogja A-t és vár B-re, P2 szál fogja B-t és vár A-ra • Megoldás: zár fa struktúra, fentről lefelé haladunk
Multi-thread vs. multi-process? • NT, VMS-en gyorsabb szálat létrehozni • UNIX-on is valamivel gyorsabb • Linux-on nincsenek igazi szálak! • Pl.: minden szálnak van külön PID-je • Core dump megöli az egész processzt
Memória kezelő modul • myalloc.c • Szegmens fogalma • Memória csorgás megszüntetése, fontossága
Memória modulok struktúrája typedef struct _AllocUnit { unsigned long Size; /* size of the chunk */ struct _AllocUnit *next; /* link to the next unit */ struct _AllocUnit *prev; /* the previous unit */ unsigned char memory[1]; /* one or more bytes reserved */ } AllocUnit, *pAllocUnit; • Fontos-e, hogy mi van közvetlenül a memory[1] mező előtt? (Alignment) • Miért nem memory[0]? • Hordozható ez a kód?
Memória „class” struct typedef struct _MyAlloc { #if MTHREAD MUTEX mxSegment; #endif void * (*memory_allocating_function)(size_t); void (*memory_releasing_function)(void *); unsigned long MaxSize,CurrentSize, MaxNetSize,MinNetSize; pAllocUnit FirstUnit; } MyAlloc, *pMyAlloc;
Fontosabb memória kezelő függvények • alloc_InitSegment • alloc_SegmentLimit • alloc_FreeSegment • alloc_FinishSegment • alloc_Alloc • alloc_Free • alloc_Merge
ScriptBasic váltózók • Nem típusos nyelv: A = 1 A = 2.3 A = ”55” A[13] = 63 A = undef Ref A = V Három alaptípus, tömb, hash (ami tömb) és referencia bármelyike lehet egy adott változó értéke.
Referencia értékű változók • Egy változó egy másikra mutat • Explicit referencia REF utasítással • Függvény argumentum ha lehet akkor referencia érték sub test(L) L = 3 end sub G = 1 test G print G sub test(L) ByVal L L = 3 end sub G = 1 test G print G sub test(L) L = 3 end sub G = 1 test ByVal G print G 3 1 1
Változó struktúra 1/2 typedef struct _FixSizeMemoryObject { union _fsmoval{ PBYTE pValue; // the value of the object long lValue; // the long value of the object double dValue;// the double value of the object struct _FixSizeMemoryObject **aValue; } Value; unsigned long Size; // the actual size used // (may be different from the size indicated by the type) BYTE sType; //index to the array SizeOfType. // If this is LARGE_BLOCK_TYPE then //Size is the memory allocated for the value BYTE vType; // the variable type, VTYPE_/LONG/DOUBLE/STRING/REF BYTE State; // state of the variable (mortal, free or assigned)
Változó struktúra 2/2 // these two pointers help to maintain // either the free list or the mortal lists // a variable can never be in a free and in a mortal list at the same time // in case of reference variable these fields maintain a linked list of // variables referencing the same value struct _FixSizeMemoryObject *next; // link to the next object union { struct _FixSizeMemoryObject *prev; // link to the previous object struct _FixSizeMemoryObject **rprev; // link to the previous variable referencing }link; long ArrayLowLimit, ArrayHighLimit; // If this is an array then these fields tell you where to start // and where to end } FixSizeMemoryObject, *pFixSizeMemoryObject;
Változók Tárolása FSMO .Value.dValue = 3.3 FSMO FSMO .Value.lValue = 3 .Value.pValue .Size=67 This is a string with possible \0 character or any characters inside
Változó „osztály” struct typedef struct _MemoryObject { // SizeOfType[i] is the size of the type i unsigned long SizeOfType[MAX_NUMBER_OF_FIX_TYPES]; // the number of fix length type memory objects // we can have at most MAX_NUMBER_OF_FIX_TYPES fix size types BYTE iNumberOfFixTypes; // LARGE_BLOCK_TYPE means large block which is not stored in free list BYTE FirstStringIndex,LastStringIndex; pFixSizeMemoryObjectMemoryObjectsFreeList[MAX_NUMBER_OF_FIX_TYPES]; ...memória allokálás szokásos... unsigned long maxderef;// 1000 by default } MemoryObject, *pMemoryObject;
Változó allokálás • malloc/free feleslegesen drága • Kis méretű változókra (<1024) szabad lista van fenntartva • sType mondja meg a lefoglalt méretet
Átmeneti változók • „Mortal” lista • Amikor befejeződik egy kifejezés kiértékelése a mortal lista elemei felszabadulnak
Változó felszabadítás • Ha nem létezne referencia változó, könnyű lenne az élet • Referencia változóval két lehetséges megoldás van: • Referencia számláló • Visszahivatkozási lánc • Nincs GC ScriptBasic-ben
Referencia változó beállítása 1/3 • memory_SetRef() A legegyszerűbb eset: REF P2 = P1 p2 vType=VTYPE_REF aValue rprev next p1 vType=VTYPE_LONG lValue=3 rprev next aValueszükséges, hogy P2 = ”aa” megváltoztassa p1->Value.lValue értéket next szükséges a referenciák felfűzéséhez (következő diák)
Referencia változó beállítása 2/3 Bonyolultabb eset: REF P3 = P2 p3 vType=VTYPE_REF aValue rprev next p2 vType=VTYPE_REF aValue rprev next p1 vType=VTYPE_LONG lValue=3 rprev next
Referencia változó beállítása 3/3 Még bonyolultabb eset: REF P4 = P3 REF P3 = P2 p4 vType=VTYPE_REF aValue rprev next p3 vType=VTYPE_XXX REF xValueaValue rprev next p2 vType=VTYPE_REF aValue rprev next p1 vType=VTYPE_LONG lValue=3 rprev next
Referencia változó beállítása 3/3 Még bonyolultabb eset: REF P4 = P3 REF P3 = P2 p4 vType=VTYPE_REF aValue rprev next p3 vType=VTYPE_XXX REF xValueaValue rprev next p2 vType=VTYPE_REF aValue rprev next p1 vType=VTYPE_LONG lValue=3 rprev next
Változó törlése referenciákkal undef P1 p4 vType=VTYPE_REF aValue rprev next p3 vType=VTYPE_REF aValue rprev next p2 vType=VTYPE_REF aValue rprev next p1 p1 vType=VTYPE_LONG lValue=3 rprev next memory_ReleaseVariable()
Referencia változó törlése referenciákkal undef P2 p4 vType=VTYPE_REF aValue rprev next p3 vType=VTYPE_REF aValue rprev next p2 vType=VTYPE_REF aValue rprev next p1 vType=VTYPE_LONG lValue=3 rprev next
Mi a helyzet ciklikus körbehivatkozásnál? undef A vType=VTYPE_REF aValue rprev next REF A[0] = A undef A 0 Ismert váltózó memória vesztési hiba. Csak számításigényes GC algoritmussal lehet kiküszöbölni. A program végén felszabadul a memória. A vType=VTYPE_ARRAY aValue rprev next
Szimbólum tábla kezelés • sym.c The dragon book: Aho-Sethi-Ulman : Compilers Principles, techniques, and Tools Addison-Wesley Publishing Company 1986 • Akit érdekel nézze meg egyénileg a sym.c fájlban, és értse meg, hogy mit csinál a program.
Naplózó modul • Tipikus és egyszerű aszinkron programozási feladat • Lehet rajta többszálú programozást tanulni • Sok köze nincs a ScriptBasic-hez
Naplózás általában • Kétféle naplózási feladat • Informatív naplózás, például web szerver access log • Tranzakciós naplózás • Szinkron és aszinkron naplózás
Naplózó modul • logger.c • Szinkron és aszinkron naplózás • A szinkron naplózás érdektelen, egyszerű, primitív
Aszinkron naplózás • Gyorsan átadjuk a naplózandó elemet, és majd valaki kiírja • Aszinkron szálon futó kiíró modul • UNIX syslog [másik] gépre UDP-n • Nincs garancia, hogy nem vész el log • Nem várakoztatja a hívót
Logger struktúra typedef struct _tLogger { char *pszFileName; char szFileName[FNMAX]; FILE *fp; long LastTime; // the hour of the log was written last time long TimeSpan; ...memória függvények szokásos... long MaxItemLen; // the maximal length of a log line ptLogItem QueueStart,QueueEnd; MUTEX mxChain; MUTEX mxRun; MUTEX mxState; int type; // 0 normal or 3 synchronous logger int state; // 0 normal, 1 currently shutting down, // 2 finished, closed, dead // 3 this is a synchronous logger } tLogger,*ptLogger;
mxRun mxChain Hogyan működik az aszinkron naplózás log_thread