Я пытаюсь использовать переменную в структуре typedef, которая хранится в другой структуре typedef. Как только я сохраню этот указатель внутри массива указателей, идентификатор переменной procHeaader теряется.
#include <stdlib.h>
#include <Arduino.h>
#include "Proc.h"
#include "../../Fat/src/Fat.h"
/*
creates a process table with a size of MAX_PROC_COUNT
*/
ProcTable * createProcTable() {
ProcTable * procTable = (ProcTable *)malloc(sizeof(ProcTable));
procTable->procCount = 0;
return procTable;
}
/*
dumps the process table
*/
void dumpProcessTable(ProcTable * table) {
Serial.println("Processes");
if(table->procCount < 1) {
Serial.println("---------------");
Serial.println("no procs running");
return;
}
for(int i = 0; i < table->procCount; i++) {
Serial.println("---------------");
Serial.println("pid | quantum");
Serial.print(table->procs[i]->header->id);
Serial.write(" ");
Serial.print(table->procs[i]->quantum);
Serial.write("\n");
}
}
/*
creates a process in the paused state
*/
Process * createProcess(ProcTable * table, Fat * fat, char * fileName) {
Process * proc = (Process*)malloc(sizeof(Process));
proc->header = (ProcHeader*)malloc(sizeof(ProcHeader));
proc->mmu = (MMU *)malloc(sizeof(MMU));
proc->header->id = table->procCount;
proc->header->state = RUNNING;
proc->quantum = MAX_QUANTUM; //TODO: change this based on how big the binary that gets loaded into it is
loadProcExecutable(proc, fat, fileName);
table->procs[table->procCount] = proc;
table->procCount++;
return proc;
}
Process * findProc(ProcTable * table, int pid) {
for(int i = 0; i <= table->procCount; i++) {
if(table->procs[i]->header->id == pid) {
return table->procs[i];
}
}
Serial.println("Tried to lookup non existent process. terminating operation.");
}
/*
cuts a process specified with pid from the proc table and decrements the procCounter
*/
void deleteProc(ProcTable * table, int pid) {
Process * procs[MAX_PROC_COUNT] = {};
for(int i = 0; i < table->procCount; i++) {
if(table->procs[i]->header->id != pid) {
procs[i] = table->procs[i];
}
}
memcpy(table->procs, procs, MAX_PROC_COUNT);
table->procCount--;
}
/*
sets the state of a process
states:
0: paused
1: running
2: terminated
this should also be used to outright kill processes
*/
void setProcState(ProcTable * table, int pid, int state) {
Process * proc = findProc(table, pid);
switch(state) {
case PAUSED:
proc->header->state = PAUSED;
break;
case RUNNING:
proc->header->state = RUNNING;
break;
case TERMINATED:
deleteProc(table, proc->header->id);
break;
}
}
/*
Loads a program into a given process space
*/
void loadProcExecutable(Process * proc, Fat * fat, char * fileName) {
fileInfo * filePtr = (fileInfo *)malloc(sizeof(fileInfo));
int fileIndex = findFileByName(fileName, fat->fileCount);
char * fileContents;
if(fileIndex == -1) {
Serial.print(fileName);
Serial.print(": no such file\n");
return;
}
getFATEntry(fileIndex, filePtr);
getFileData(*filePtr, fileContents);
writeMemoryChunk(proc->mmu, fileContents, 0, sizeof(fileContents)/sizeof(char));
}
void startNextProc(ProcTable * table) {
table->procs[table->procCount-1]->header->state == RUNNING;
}
/*
updates all processes timers. If any process has run out of time, it will be killed
*/
void updateProcessQuantums(ProcTable * table, int cycleTime) {
if(table->procCount == 0) {
return;
}
for(int i = 0; i <= table->procCount; i++) {
if(table->procs[i]->quantum - cycleTime < 0) {
if(!table->procs[i]->interpreter->finished) {
table->procs[i]->header->state = PAUSED;
}
//dump a message
Serial.print("killing pid: ");
Serial.print(table->procs[i]->header->id);
Serial.println(" quantum expired");
//kill the process
setProcState(table, table->procs[i]->header->id, TERMINATED);
//see what proc is next in line
startNextProc(table);
return;
}
if(table->procs[i]->header->state == PAUSED) {
continue;
}
if(table->procs[i]->header->state == RUNNING) {
table->procs[i]->quantum -= 1;
// InterpretOneCycle(table->procs[i]->interpreter, &table->procs[i]->header->pc, table->procs[i]->mmu->memUsed);
// if(table->procs[i]->interpreter->finished) {
// setProcState(table, table->procs[i]->header->id, TERMINATED);
// startNextProc(table);
// }
}
}
return;
}
заголовочный файл:
#define PROC_MEM_SIZE 0x200
#define MAX_PROC_COUNT 0x9
#define MAX_QUANTUM 1000000 //ticks
#define PAUSED 0
#define RUNNING 1
#define TERMINATED 2
typedef struct {
char * stack;
int id;
int state;
int sp;
int loopAddr;
int pc;
} ProcHeader;
typedef struct {
ProcHeader * header; //contains global information about the process
unsigned int memOffset; //this is for the interpreter to know where to execute its opcodes
long int quantum; //time slot for the process
Interpreter * interpreter; //Interpreter that will execute opcodes
MMU * mmu; //Manager for process memory
} Process;
typedef struct {
Process * procs[MAX_PROC_COUNT];
int procCount;
} ProcTable;
ProcTable * createProcTable();
Process * createProcess(ProcTable * table, Fat * fat, char * filename);
void setProcState(ProcTable * table, int pid, int state);
void dumpProcessTable(ProcTable * table);
void updateProcessQuantums(ProcTable * table, int cycleTime);
void loadProcExecutable(Process * proc, Fat * fat, char * fileName);
метод вызывающего абонента:
Kernel * initKernel() {
Kernel * kernel = (Kernel*)malloc(sizeof(Kernel));
kernel->procTable = createProcTable();
kernel->fat = createFAT();
return kernel;
}
заголовок вызывающего абонента:
typedef struct {
ProcTable * procTable;
Fat * fat;
int debugMode;
int cycleDuration;
} Kernel;
Kernel * initKernel();
Process * createProcess(ProcTable * table);
Как только я просматриваю записи массива procs, идентификатор процесса, который он возвращает - что-то число. Почему это так?
Для отладки используется следующая функция:
for(int i = 0; i < table->procCount; i++) {
Serial.println("---------------");
Serial.println("pid | quantum");
Serial.print(table->procs[i]->header->id); //returns 1256?
Serial.write(" ");
Serial.print(table->procs[i]->quantum);
Serial.write("\n");
}