int bridge_control (int port_index,UID_CNTRL_BODY_T* cntrl) { switch (cntrl->cmd) { case UID_PORT_CONNECT: #ifdef MY_PRINT_RSTP printf("connected port p%02d\n", port_index); #endif BitmapSetBit(&enabled_ports, port_index - 1); STP_IN_enable_port (port_index, True); break; case UID_PORT_DISCONNECT: #ifdef MY_PRINT_RSTP printf("disconnected port p%02d\n", port_index); #endif BitmapClearBit(&enabled_ports, port_index - 1); STP_IN_enable_port (port_index, False); break; case UID_BRIDGE_SHUTDOWN: #ifdef MY_PRINT_RSTP printf("shutdown from manager :(\n"); #endif return 1; default: printf("Unknown control command <%d> for port %d\n", cntrl->cmd,port_index); } return 0; }
int fs_creat(byte *path, word mode, word rights) { // otevre se pro cteni zapis MNODE *DirNode; int i,j,MySystemIndex; TaskUArea *Task = GetCurrentTaskUArea(); word MyPackID, CallResult, GetNumber, MyIndex; byte buffer[255],*dir,trunc; byte sector[512]; MNODE *MyNode = (MNODE *) sector; dword Node; word CacheFlag; SyscallActive = 1; CacheFlag = (mode & IO_CACHE_THROUGH) ? FPACK_NOTHING : FPACK_ADD; Task->ErrorLevel = ERR_FS_NO_ERROR; MyIndex = BitmapGetFirstHole(Task->Bmp,MaxOpenedFiles); // for (i=5; i<MaxOpenedFiles; ++i) // if (!Task->OpenFiles[i].Used) { MyIndex = i; break; } if (MyIndex == 0xffff) { Task->ErrorLevel = ERR_TOO_MANY_OPENED_FILES; SyscallActive = 0; return -1; } dir = new byte [strlen(path)+1]; strcpy(dir,path); CutLastPathPart (dir,buffer); CallResult = NAMEN( dir, DirNode, CacheFlag); if ( CallResult != ERR_FS_NO_ERROR) { delete [] dir; Task->ErrorLevel = CallResult; SyscallActive = 0; return -1; } CallResult = SearchDirByName(DirNode, buffer, Node, CacheFlag, 0); if ( CallResult == ERR_DIRREC_NOT_FOUND) { // soubor jeste nexistuje, vypln jeho node trunc = 0; memset(sector,0,512); memcpy(MyNode->MagicWord,FileMagicWord,8); memcpy(MyNode->MagicWordII,FileMagicWord,8); MyNode->OwnerID = Task->ownerID; MyNode->GroupID = Task->groupID; MyNode->Type = NODE_TYPE_FILE; MyNode->Rights = rights; GlobalTime.Get(MyNode->FileAccessed); MyNode->FileModified = MyNode->FileAccessed; MyNode->NODEAccessed = MyNode->FileAccessed; MyNode->NODEModified = MyNode->FileAccessed; MyNode->Size = 0; MyNode->Links = 1; MyNode->Device = DirNode->Device; MyNode->Partition = DirNode->Partition; CallResult = CacheManAllocateSector( MyNode->Device, MyNode->Partition, 0, 1, MyNode->logical,GetNumber, MyPackID, FPACK_CREAT); if (CallResult != ERR_FS_NO_ERROR) { DirNode->Locked.Release(); ActiveNodes->Release(DirNode); delete [] dir; } MyNode->packID = MyPackID; } else if (CallResult == ERR_FS_NO_ERROR) { // soubor uz existuje -> zkrati se na 0 trunc = 1; ActiveNodes->Add(DirNode->Device, DirNode->Partition, Node, MyNode); } else { // chyba pri pristupu k adresari DirNode->Locked.Release(); ActiveNodes->Release(DirNode); delete [] dir; } // DirNode je v tabulce aktivnich nodu zamceny // trunc = 1 MyNode je v tabulce aktivnich nodu odemceny ->nelze ho smazat // trunc = 0 MyNode je vyplnen v pameti // pristup k systemove tabulce, zjisti prvni volnou diru SystemTableSem->Down(); Task->OpenFiles[MyIndex].SystemTabIndex = BitmapGetFirstHole(SystemOpenFilesBmp, MaxOpenedFiles); if (Task->OpenFiles[MyIndex].SystemTabIndex == 0xffff) { SystemTableSem->Up(); DirNode->Locked.Release(); ActiveNodes->Release(DirNode); if (trunc) { ActiveNodes->Release(MyNode); } Task->ErrorLevel = ERR_TOO_MANY_OPENED_FILES; delete [] dir; SyscallActive = 0; return -1; } BitmapSetBit(SystemOpenFilesBmp, Task->OpenFiles[MyIndex].SystemTabIndex); SystemTableSem->Up(); MySystemIndex = Task->OpenFiles[MyIndex].SystemTabIndex; if (trunc) { // soubor se urizne na velikost 0 CallResult = DeleteMNODEData(MyNode, CacheFlag); if (CallResult != ERR_FS_NO_ERROR) { DirNode->Locked.Release(); ActiveNodes->Release(DirNode); ActiveNodes->Release(MyNode); // obnov bitmapu systemove tabulky SystemTableSem->Down(); BitmapClearBit(SystemOpenFilesBmp, MySystemIndex); SystemTableSem->Up(); Task->ErrorLevel = CallResult; delete [] dir; SyscallActive = 0; return -1; } CacheManCommitPackage(MyNode->packID); } else { // ulozi se node a zapise se do direktorare CallResult = CacheManSaveSector(MyNode->Device, MyNode->Partition, MyNode->logical, 1, MyPackID, FPACK_ADD /*CacheFlag*/, MyNode); if (CallResult != ERR_FS_NO_ERROR) { DirNode->Locked.Release(); ActiveNodes->Release(DirNode); // obnov bitmapu systemove tabulky SystemTableSem->Down(); BitmapClearBit(SystemOpenFilesBmp, MySystemIndex); SystemTableSem->Up(); Task->ErrorLevel = CallResult; delete [] dir; SyscallActive = 0; return -1; } // pridej do adresare zaznam o novem souboru CallResult = AddDirectoryEntry( DirNode, MyNode->logical, CacheFlag, buffer, 0); if (CallResult != ERR_FS_NO_ERROR) { DirNode->Locked.Release(); ActiveNodes->Release(DirNode); // obnov bitmapu systemove tabulky SystemTableSem->Down(); BitmapClearBit(SystemOpenFilesBmp, MySystemIndex); SystemTableSem->Up(); Task->ErrorLevel = CallResult; // uvolni sektor, ktery je naalokovan pro node CacheManFreeSector(MyNode->Device, MyNode->Partition, MyNode->logical, 1, MyPackID, FPACK_ADD/*CacheFlag*/); delete [] dir; SyscallActive = 0; return -1; } CacheManCommitPackage(MyNode->packID,FPACK_DELETE); ActiveNodes->Add(MyNode->Device, MyNode->Partition, MyNode->logical, MyNode); } // MyNode je v tabulce aktivnich uzlu odemceny OpenFiles[MySystemIndex].Used = 1; OpenFiles[MySystemIndex].Access = IO_CAN_BOTH; OpenFiles[MySystemIndex].Access |= (CacheFlag == FPACK_NOTHING) ? IO_CACHE_THROUGH : IO_CACHE_ADD; OpenFiles[MySystemIndex].Position = 0; OpenFiles[MySystemIndex].DirtyBuffer = 1; OpenFiles[MySystemIndex].BufferPos = 0; OpenFiles[MySystemIndex].Buffer = new byte[512]; OpenFiles[MySystemIndex].LastPreload = 0; OpenFiles[MySystemIndex].MemNODE = MyNode; Task->OpenFiles[MyIndex].Bitmap = new byte[(MaxOpenedFiles>>3)+1]; memset(Task->OpenFiles[MyIndex].Bitmap,0,(MaxOpenedFiles>>3)+1); // podiva se jestli uz proces neotevrel stejny soubor, // pokud ano do bitmapy si zanese jeho indexy a svuj index // zanese do jeho bitmapy (pokud nejakou ma) if (trunc) for (i=5,j=Task->NrOpenedFiles-5; i<MaxOpenedFiles; ++i) { if (!j) break; if ((i != MyIndex) && (Task->OpenFiles[i].Used)) { if (MyNode == OpenFiles[Task->OpenFiles[i].SystemTabIndex].MemNODE) { if (Task->OpenFiles[i].Bitmap) BitmapSetBit(Task->OpenFiles[i].Bitmap, MyIndex); BitmapSetBit(Task->OpenFiles[MyIndex].Bitmap, i); } j--; } } Task->OpenFiles[MyIndex].Used = 1; Task->NrOpenedFiles++; BitmapSetBit(Task->Bmp,MyIndex); DirNode->Locked.Release(); ActiveNodes->Release(DirNode); delete [] dir; SyscallActive = 0; return MyIndex; }
int fs_close(int index) { TaskUArea *Task = GetCurrentTaskUArea(); MNODE *MyNode; word MySysIndex; int i,j; SyscallActive = 1; Task->ErrorLevel = ERR_FS_NO_ERROR; if (!Task->OpenFiles[index].Used) { Task->ErrorLevel = ERR_NOT_VALID_FILE_HANDLE; SyscallActive = 0; return -1; } MySysIndex = Task->OpenFiles[index].SystemTabIndex; MyNode = OpenFiles[MySysIndex].MemNODE; if (OpenFiles[MySysIndex].Access & IO_CACHE_ADD) CacheManCommitPackage(MyNode->packID); ActiveNodes->Release(MyNode); OpenFiles[MySysIndex].Used = 0; delete OpenFiles[MySysIndex].Buffer; SystemTableSem->Down(); BitmapClearBit(SystemOpenFilesBmp, MySysIndex); SystemTableSem->Up(); if (MyNode) { // odmaz se z bitmap u ostatnich for (i=5,j=Task->NrOpenedFiles-6; i<MaxOpenedFiles; ++i) { if (!j) break; if ((i != index) && (Task->OpenFiles[i].Used)) { if (MyNode == OpenFiles[Task->OpenFiles[i].SystemTabIndex].MemNODE) { if (Task->OpenFiles[i].Bitmap) BitmapClearBit(Task->OpenFiles[i].Bitmap, index); } j--; } } } // BitmapClearBit(Task->OpenFiles[index].Bitmap,index); Task->OpenFiles[index].Used = 0; Task->NrOpenedFiles--; BitmapClearBit(Task->Bmp,index); delete Task->OpenFiles[index].Bitmap; SyscallActive = 0; return 0; }