The whole code creating function without subfunctions to calculate value and/or insert values to the array:
Code:
LZSBYTE LzsCompileSegmentTable(tLzsSegTabEntry LZSFAR *pSegTab_i,
LZSUINT unSegTabEntries_i, LZSWORD wTask_i) {
LZSWORD wNativeCodeArraySize; //Size of Native Code array for this Ucode Segment
LZSWORD wUCodeNCodeMapSize; //Size of mapping tables for UCode# to position in Segments
LZSWORD wJumpTableSize; //Amount of jumps in Code
LZSWORD wDSInSegTab; //Number of data segments in seg table
tLzsSegTabEntry LZSFAR *pSegmentTable; //Pointer to SegmentTable
tLzsCompilationUnit *CompilationList; //List of Compilation Units
tPlcMemPtr pPrimarySegment; //Primary entry in Seg Table
tPlcMemPtr pSecondarySegment; //Secondary entry in seg table
tPlcMemPtr pToFree; // Pointer to memory that can be freed
LZSWORD wTemp;
LZSBYTE bRetCode;
LZSUINT i;
pSegmentTable = pSegTab_i;
wDSInSegTab = 0;
bRetCode = 0;
pToFree = LZSNULL;
for (i = 0; i < unSegTabEntries_i; i++) {
pPrimarySegment = pSegmentTable->m_pPrimarySeg;
if (pPrimarySegment != LZSNULL && 0x01 == pPrimarySegment[2]) { //Current Segment is a data segment
if (pSegmentTable->m_pSecundarySeg != LZSNULL) {
pToFree = LzsSegGetAddr(i, kPlcSegNativeCode);
LZSFREE(pToFree);
}
wDSInSegTab++;
}
pSegmentTable++;
}
//Total number of data segments is now in wDSInSegTab
//Every Datasegment needs to be linked to a single Native Code block.
CompilationList = (tLzsCompilationUnit*) LzsEnvMemAlloc(wDSInSegTab
* sizeof(tLzsCompilationUnit));
//Every compile unit includes all necessary information to compile the code with the according data segment
pDataSegmentNativeSegmentMap_g = (tLzsCompilationTable *) LzsEnvMemAlloc(
wDSInSegTab * sizeof(tLzsCompilationTable));
wDataSegmentNativeSegmentMapSize_g = wDSInSegTab;
//Iterate through all datasegments in segment table -> Calculate sizes for each datasegment in a
//first compiler pass through then allocate all necessary memory.
wDSInSegTab = 0;
pSegmentTable = pSegTab_i;
for (i = 0; i < unSegTabEntries_i; i++) {
wNativeCodeArraySize = 0;
wUCodeNCodeMapSize = 0;
wJumpTableSize = 0;
pPrimarySegment = pSegmentTable->m_pPrimarySeg;
if (pPrimarySegment != LZSNULL && 0x01 == pPrimarySegment[2]) { //Current Segment is a data segment
pSecondarySegment = pSegmentTable->m_pSecundarySeg;
bRetCode
= CompilerFirstPass(pPrimarySegment, pSecondarySegment,
&wNativeCodeArraySize, &wUCodeNCodeMapSize,
&wJumpTableSize);
if (bRetCode != 0) {
return bRetCode;
}
pDataSegmentNativeSegmentMap_g[wDSInSegTab].m_pNativeCodeSegment.m_pArray
= (LZSBYTE *) LzsEnvMemAlloc(wNativeCodeArraySize);
pDataSegmentNativeSegmentMap_g[wDSInSegTab].m_pNativeCodeSegment.m_wOffset
= 0;
pDataSegmentNativeSegmentMap_g[wDSInSegTab].m_wDataSegmentInst = i;
CompilationList[wDSInSegTab].m_wNativeCodeSegmentSize
= wNativeCodeArraySize;
CompilationList[wDSInSegTab].m_pUCodeSegment = pSecondarySegment;
CompilationList[wDSInSegTab].m_wDataSegmentInst = i;
CompilationList[wDSInSegTab].m_arrNCodeMap
= (LZSWORD *) LzsEnvMemAlloc(wUCodeNCodeMapSize
* sizeof(LZSWORD));
CompilationList[wDSInSegTab].m_arrUCodeMap
= (LZSWORD *) LzsEnvMemAlloc(wUCodeNCodeMapSize
* sizeof(LZSWORD));
CompilationList[wDSInSegTab].m_arrPatchPos
= (LZSWORD *) LzsEnvMemAlloc(wJumpTableSize
* sizeof(LZSWORD));
CompilationList[wDSInSegTab].m_arrTargetPos
= (LZSWORD *) LzsEnvMemAlloc(wJumpTableSize
* sizeof(LZSWORD));
CompilationList[wDSInSegTab].m_wJumps = wJumpTableSize;
CompilationList[wDSInSegTab].m_wOPCodes = wUCodeNCodeMapSize;
CompilationList[wDSInSegTab].m_pNativeCodeSegment
= &pDataSegmentNativeSegmentMap_g[wDSInSegTab].m_pNativeCodeSegment;
wDSInSegTab++;
}
pSegmentTable++;
}
//Compile every Compilation Unit
for (i = 0; i < wDSInSegTab; i++) {
bRetCode = CompilerSecondPass(&CompilationList[i], wTask_i);
if (bRetCode != 0) {
return bRetCode;
}
bRetCode = FixJumpsForSegment(&CompilationList[i]);
if (bRetCode != 0) {
return bRetCode;
}
}
FreeCompilationUnits(CompilationList, wDSInSegTab);
return bRetCode;
}
The whole calling function:
Code:
LZSBYTE LzsNccCallNc(tPlchInst hChildInst_p, LZSDWORD dOffset_p) {
LZSBYTE LZSFAR* AnfNS; //Pointer to the start of NC
tPlcMemPtr pAdrDS; //Pointer to the start of the DS that is bound to the nc
tPlcMemPtr pNS; //Another pointer to nc
tSegHeader SegHdrInf; //Stores Header information for a segment
LZSBYTE bHeaderSize; //Header size for a segment
LZSBYTE (*NC_fct)(LZSDWORD, LZSDWORD, LZSDWORD); //Function definition for calling nc
LZSBYTE bRetCode; /* ErrorCode of function */
bRetCode = kLzsSuccess;
pNS = LZSGetNcAddressForDS(hChildInst_p);
LzsMemGetSegHeader(pNS, &SegHdrInf);
bHeaderSize = LzsMemAbsGetByte((LZSBYTE LZSFAR*) &SegHdrInf.m_HeaderSize);
/*we also need the adress of DataSegment */
pAdrDS = LzsSegReadSegAddr(hChildInst_p, LZSPRIMARY);
/* Update the NC Help Segment, we could have changed the instance */
LzsNccUpdateInstInHelpSeg(hChildInst_p);
AnfNS = pNS;
AnfNS += bHeaderSize; /* skip header info */
NC_fct = (LZSBYTE(*)()) AnfNS;
bRetCode = (*NC_fct)((LZSDWORD) pSegTab_l, (LZSDWORD) pAdrDS,
(LZSWORD) hChildInst_p);
if (bRetCode) {
return bRetCode;
}
return bRetCode;
}
So I do not have any of that permission stuff in any more. So I am back to guessing whats wrong. Right now if I have native code which is just i = i + 1; It sometimes runs and sometimes doesn't, I am not joking here, sometimes when I start debugging it is perfectly fine and sometimes I get SIGILL at the first Instruction. Again, the nc which is stored somewhere else in the memory, not far just about 1kb or so, is running fine every damn time.
The only difference is the location in the memory, as far as I can tell.