Frequently Asked Questions
This page contains answers to common questions handled by our customer support staff, along with some tips and tricks that we have found useful and presented here as questions.
Please consult the generic EDE FAQ for questions related to the Embedded Development Environment.
Contents
- "CodeBase Error at ###### in the CodeSense file parsing thread". What to do?
- I get C++ error E135: namespace "std" has no member "xxx". How can I use the C library in the std namespace?
- Global C++ objects seems to be uninitialized after startup when using an RTOS. What is wrong?
- Can EDE generate my project's make file from the command line?
- I use my own low level I/O routines. How do I get rid of the unused File System Simulation (FSS) sections listed in my map file?
- I get C++ error E349. How can I use memory qualifiers in C++?
- How to set up CAN Debugging using the IXXAT CANdy Lite module?
- CrossView Pro prompts: "cannot find ws2_32.dll". Where can I find this file?
- CrossView is using the NMI interrupt vector for debugging. How can I change this interrupt debug vector, freeing up the NMI for my application?
- The treatment of far pointers is not what I expect. I thought that far pointers should be compared as 4 bytes and not 2 bytes pointers. What is wrong?
- Which C-libraries functions are not reentrant?
- I use the _getbit() and _putbit() built-in functions for accessing individual bits in a bitaddressable object. I tried to use a runtime variable to specify the bit-offset argument in these functions, but the compiler tells me to use a constant value. Why?
- I have defined a bit variable using the _atbit() attribute. When I declare this bit as an external variable in a different module, the linker complains about an unresolved reference. Why?
- I have a piece of conditional code in my application for which the compiler generates no code at all! I also have a piece of conditional code that is executed unconditionally. Why?
- How to show local static variables in my map file?
- What is Task Concept and what is Flat Interrupt Concept? What should I know about it?
- Some sections cannot be located, how can I find out why?
- I got error message E282: "data section 'C166_DGROUP' cannot be located in one page". What must I do to get rid of it?
- When building an application, how can I locate a code section or data section at a specific absolute address?
- I have some external routines at fixed addresses. How can I call these routines from within my application?
- I want to exchange data with an external source, but the problem is that floating point values are passed as little-endian (reverse storage order). How can I set things right in my program?
- How can I avoid my non-initialized variables to be cleared at startup?
- I am using a C167CR and wondering why the CAN-registers are not defined in the register definition files. Can I simply add these definitions?
- Why is there a user stack and a system stack? What do I need to know about these stacks?
- Can I change the user stack size, and how can I do that?
- Can I change the system stack size, and how can I do that?
- Using the HEAPSIZE control seems to have no effect.
- If I define a far or huge character pointer and initialize it with a string constant, the compiler still puts the string constant in a normal data section. Is this a compiler problem?
- I have trouble running your C166/ST10 (evaluation) package. It seems to run software from other tool suppliers. Can you tell me what is wrong?
- I want to minimize interrupt latency by using '#pragma noframe' in my interrupt routines. Can I safely omit the saving and restoring of the DPP0 and DPP2 registers?
- I am getting multiple warnings "W118: unresolved symbol" when building my C++ project. Can I safely ignore these warnings?
- My CAN application does not work anymore after using the C167CR GA or JA Step. Why?
- Is your question not listed? Contact TASKING.
"CodeBase Error at ###### in the CodeSense file parsing thread". What to do?
Probably this is the result of a corrupt CodeSense database. The problem should disappear after a complete rebuild of the CodeSense database. Follow the next steps:
-quit EDE
-delete directory project_name.CS_ from your project directory
-delete file project_name.sbl from your project directory
-start EDE
Codewright will now create the database again. For large projects, this may take several minutes to finish. The proces can be followed by the progress indicator on the status bar. If you interrupt this proces, for example by quitting EDE, the CodeSense database can become corrupt.
I get C++ error E135: namespace "std" has no member "xxx". How can I use the C library in the std namespace?
The default C library is not in the "std" namespace. Therefore you have to specify the namespace yourself:
Instead of using namespace std; you can also write: std::atoi ("123");
Global C++ objects seems to be uninitialized after startup when using an RTOS. What is wrong?
When using an RTOS, function "main" is often already defined inside the kernel. The global and static object instantiations are taken care of by a special function call _main(). The C++ compiler generates a call to this routine when it encounters the main function. The RTOS task will likely not have a main function in its C++ code and therefore not have the _main() call.
To correct this, please call _main() manually right after task initialisation. For example:
Can EDE generate my project's make file from the command line?
Yes, run the following command:
ede.exe -X"SysQuit" example.psp project.pjt
Or use this command for running EDE minimized and without splash screen:
start /WAIT /MIN ede.exe -X"SysQuit" example.psp project.pjt -NOSPLASH
Note: If the generated make file is exactly the same as the already existing make file, the original file will not be replaced. If the file time must be updated always, you can delete the existing make file first.
I use my own low level I/O routines. How do I get rid of the unused File System Simulation (FSS) sections listed in my map file?
Since toolchain v7.0r1, File System Simulation (FSS) has been introduced. Instead of the functions io_read and io_write, the new functions _read and _write are being used as low level I/O routines. To get rid of the other FSS functions, you must override low level library function _lseek as well. To do so, add the following function definitions to your program:
I get C++ error E349. How can I use memory qualifiers in C++?
If you want to use memory qualifiers like _far and _(s)huge in your C++ project, you must place the memory qualifier after the member or operator-overloading function. In the example below, an operator-overloading function for a huge object is defined and a member function for a far object.
You must define operator-overloading or member functions for every memory type that has an as such qualified object calling that specific function. The C compiler needs all these variations in order to generate the right code to handle the different pointer types. This allows the C compiler to optimize a _near variant better than a _huge variant.
Please note that the C++ compiler may generate automatic variables with a storage qualifier. The C compiler will ignore this qualifier with the message:
W 201: automatic/parameter cannot have storage type – ignored
A second problem can occur if you have a non-qualified object and only one qualified function. The C++ compiler assumes it can cast the object pointer, where in fact it cannot. The default object is cast to the qualification of the function and the C compiler does not generate a warning because the cast is correct. The result, however, is wrong. As a guideline to prevent this problems always define a default non-qualified method!
How to set up CAN Debugging using the IXXAT CANdy Lite module?
Check you have the correct IXXAT product drivers:
- The IXXAT CAN VCI driver must be Version 2.12.
- Also the passive add-on (V2.12) must be installed.
(The IXXAT VCI Driver can be downloaded from the IXXAT web site by all registered users.)
Go to the dialog box Project | Project Options | CrossView Pro | ROM/RAM Monitor Communication Setup and select the following items:
- Communication type: CAN
- CAN card manufacturer: IXXAT VCI
- CAN interface card: USB2CAN (The USB-to-CAN card has the same identifier as the CANdy Lite parallel)
Click on CAN Communication Setup and specify the following items:
- CAN baud rate: 500
- CAN identifier: 30
- CAN interrupt number: 7
- CAN board segment: 1
CrossView Pro prompts: "cannot find ws2_32.dll". Where can I find this file?
From toolchain v7.5r1, CrossView Pro requires the DLL ws2_32.dll which is not standard available on Windows 95 systems without any service pack installed. If you start up CrossView Pro and get a message that it cannot find the ws2_32.dll, you should either install Windows 95 Service Pack 1 or download the DLL.
CrossView is using the NMI interrupt vector for debugging. How can I change this interrupt debug vector, freeing up the NMI for my application?
By default, CrossView is using the NMI vector for setting breakpoints and single stepping. To free up the NMI vector for your application, you can change the debug trap number. To do so, add the macros DNR and DDEBUG_INT to the makefile of the monitor as stated below. This makefile is located in the c166\mon\mon167 directory. For example, to change the NMI vector (trap number 2) to trap number 8:
To rebuild the monitor, make the mon167 subdirectory the current working directory and type:
c:\c166\bin\mk166 clean
This will remove all files (*.sre, *..map, *.obj and *.ilo files) which were created before when building the monitors and boot programs. Now type:
c:\c166\bin\mk166
This invocation of mk166 will execute the make file called "makefile". As a result, the S-Record files (*.sre) of the boot programs and monitors are created in the mon167 subdirectory. You must copy the boot and monitor files you want to use (as stated in your configuration file) from this subdirectory to the c166\etc directory.
The treatment of far pointers is not what I expect. I thought that far pointers should be compared as 4 bytes and not 2 bytes pointers. What is wrong?
In the C166 language implementation, address arithmetic for 4-byte far pointers is defined to be 14-bits (page offset only). See page 3-21 in the compiler manual. This 14-bit address arithmetic is the major reason why using far pointer operations is much more efficient than huge pointer operations (which use 32-bit address arithmetic).
In the C language definition (K&R 2nd edition, section 5.4 "Address Arithmetic"), the valid pointer operations are listed:
- assignment of pointers of the same type
- adding or subtracting a pointer with an integer
- subtracting or comparing two pointers to members of the same array
- assigning or comparing to zero
NOTES:
- C does not allow to directly compare pointers to different objects. If the compiler does allow it and the objects are not located in the same page, you will yield an erroneous result for far pointers. You will yield a correct result when using huge pointers.
- In case of assigning or comparing to zero (valid pointer operation #4) comparing the offset is not enough and in that case the page is checked too.
- Combining the far pointer 14-bit address arithmetic with the valid pointer operations does imply that the size of far objects is limited to 16K.
Which C libraries functions are not reentrant?
| <assert.h> | The macro assert is not reentrant. |
| <errno.h> | errno is not reentrant. |
| <locale.h> | The function localeconv is not reentrant. |
| <malloc.h> | All functions are not reentrant. |
| <math.h> | All functions are reentrant from v7.0r0. For older versions all functions are not reentrant because they use floating point arithmetic. |
| <setjmp.h> | the functions setjmp and longjmp are not reentrant. |
| <stdio.h> | only sprintf and sscanf are reentrant. All other I/O functions share global structures. |
| <stdlib.h> | malloc, calloc, realloc and free are not reentrant (see above with ). atexit is not reentrant. For proper functioning of exit and abort, the macro EX_AB should not be set when processing start.asm. |
| <string.h> | strtok and variants (_hstrtok, _fstrtok, _sstrtok) are not reentrant. |
| <time.h> | The functions asctime, ctime, difftime, gmtime, localtime, mktime, strftime, and _tzset are not reentrant. |
I use the _getbit() and _putbit() built-in functions for accessing individual bits in a bitaddressable object. I tried to use a runtime variable to specify the bit-offset argument in these functions, but the compiler tells me to use a constant value. Why?
The _getbit() and _putbit() built-in functions provide a way to utilize the C166/ST10 bit-manipulation instructions in your C-program without having to insert pieces of inline assembly. The function arguments are mapped directly into C166/ST10 instruction operands. Example:
| C-syntax | Generated C166 assembly |
|---|---|
| bitflag = _getbit(P0, 4); | BMOV _bitflag, P0.4 |
| _putbit(_getbit(P0,0),P0,1); | BMOV P0.1, P0.0 |
Due to the nature of the C166/ST10 Family architecture, the bit-addressable memory areas can only be accessed through direct addressing, i.e. the address must be known at link/locate time. Hence, the same restrictions apply to the _getbit() and _putbit() functions.
I have defined a bit variable using the _atbit() attribute. When I declare this bit as an external variable in a different module, the linker complains about an unresolved reference. Why?
When you define a bit-variable using the _atbit attribute, you name a bit within an existing bitword or SFR variable. You do not actually allocate a bit in the C166/ST10 memory space, but merely give a bit in an existing bitaddressable object its individual name. A bit definition with _atbit() is similar to a preprocessor definition using #define. The compiler will not generate an object or reference to an object for it, and the linker/locator is unaware of its existence. Hence, you cannot declare it as an external variable.
The correct way to declare an _atbit() bit in your application is to include the complete definition in every module where it is used, preferably in a header file.
I have a piece of conditional code in my application for which the compiler generates no code at all! I also have a piece of conditional code that is executed unconditionally. Why?
The reason is often that the compiler assumes that the test condition yields invariantly true or false at runtime. In such case, the compiler will perform optimizations by removing the condition test and the never-to-be-executed branch of code. EXAMPLE:
The compiler will generate an eternal loop here without code for testing the loop condition. This is a valid optimization, since the variable port_rdy is always zero at the test point, thus the condition is always true.
This may not be what you had in mind, since port_rdy might represent a memory-mapped peripheral register, or is a global variable that is written to by an interrupt service routine. In such case you must explicitly tell the compiler that the variable can be changed behind its back. By adding the volatile type qualifier to the variable definition/declaration, you force the compiler to actually perform the variable manipulations that you coded.
Following code will work as intended: EXAMPLE:
How to show local static variables in my map file?
Local variables are not shown in your map file, because they have a limited lifetime and do not have fixed addresses in memory. However, static local variables do have a fixed address and they are not shown in the map file as well. To overcome this problem, use linker/locator option SYMB, and be sure compiler option -g (enable symbolic debug information) is switched on. Now, static variables with their absolute addresses will be listed in the map file too. However, SYMB will also add other symbolic debug information to your map file, which will make it less convenient to read.
What is Task Concept and what is Flat Interrupt Concept? What should I know about it?
The very first C166 compiler originated from Siemens. Its design reflected the task-oriented nature of the SAB 80C166 microcontroller. It introduced an extra scope level between local and global (or module and application) scope: the TASK scope. This concept allowed for a high grade of modularity and code-reusability.
The TASKING C166 compiler was designed with this concept in mind. The Task Concept was implemented by running a separate linker and locator phase in the L166 linker/locator. The first phase links all object modules into a Task Object module (default extension is .LNO). In this phase all references within the task are resolved and libraries can be linked which are called solely by functions in this task. The second phase takes all Task Object modules together and locates the application into memory.
In practice, most users did not use this feature and linked their entire application into a single task. Besides, we noticed that many customers found the unusual concept too restrictive and awkward to use. Therefore, in version 3.0 of its C166 toolset, TASKING introduced the Flat Interrupt Concept.
In the Flat Interrupt Concept, the Task scope level is not used. This means that the link phase can be skipped. There is just one user stack, a single heap, one floating point stack, and library routines can be called throughout the application. An important side effect is that the overall size of the application tends to be more compact. The Flat Interrupt Concept is the approach which most commonly implemented in embedded toolchains.
The Embedded Development Environment (EDE) will by default use the Flat Interrupt Concept. In most situations this will be the right choice. You should consider using Task Concept only when:
- Your realtime kernel requires it.
- When your software design approach requires a high grade of modularity and code-reusability.
When using EDE and Task Concept, you should define separate projects for all tasks. For locating all tasks into a an application you will need another separate project.
For more details, refer to Chapter 2 "Software Concept" of the A166 Assembler User's Manual.
Some sections cannot be located, how can I find out why?
The best way to figure out why a section cannot be located is to look in the map file to see what the attributes of that section are. The following attributes are important:
- SECTION type: The section type gives the locator restrictions on where the section is allowed to be located. An LDAT section for example, is a 'near data'-section. Hence, you must make sure that the specified memory range can be addressed through one of the DPPn registers. In addition, you cannot have more than 64kb of such memory.
- ALIGN type: For instance PECADDRESSABLE and BITADDRESSABLE give the locator restrictions of where a section is allowed to be located.
- MEMORY type: ROM typed sections cannot be located in RAM and Internal RAM areas and vice versa.
- GROUP name: The locator wants to locate all DATA sections with the same group name in one 16K page and all CODE sections with the same group name in one 64K segment.
- CLASS name: You may have specified a range for a class which is not large enough to hold all its sections.
In most situations the combination of the restrictions is the reason that the locator is not able to place the section at a valid memory location.
I got error message E282: "data section 'C166_DGROUP' cannot be located in one page". What must I do to get rid of it?
When compiling in large memory model, all objects defined which do not exceed a threshold size of 256 bytes, are put into a near data section in the default data group. When the accumulated default data of all modules exceeds 16K, the linker/locator will issue this error message. By definition, applications built with Large Data model can only have a single 16K data page of default near data. The solution is to decrease the size of the default data group. Here are some ways to do it and please note that these approaches can be combined to produce the desired effect:
Decrease the default data Threshold value. EDE: in the Project Options | C Compiler | Allocation Variables dialog box, decrease the listed Threshold value. This will reduce the number of variables stored into default data. Command Line: use C166 compiler option -Tvalue to specify a new threshold value (default = 256). Explicitly exclude data objects from the default data group by defining/declaring them with the 'far' storage specifier.
See also section 3.2.1.6 "Efficiency in Large Data Models" in the C User's Manual.
When building an application, how can I locate a code section or data section at a specific absolute address?
You can tell the compiler to start an absolute code or data section by means of the following pragma:
The abbreviation mem is a memory code as shown in the next table:
| Description | Mem Code | Class Name | Example Section Name |
|---|---|---|---|
| bits | BI | CBITS | MOD_1_BI |
| strings/fp const. | CO | CROM | MOD_2_CO |
| bitwords | BA | CBITWORDS | MOD_3_BA |
| near data | NB | CNEAR | MOD_4_NB |
| far data | FB | CFAR | MOD_5_FB |
| huge data | HB | CHUGE | MOD_6_HB |
| shuge data | XB | CSHUGE | MOD_7_XB |
| functions | PR | CPROGRAM | MOD_8_PR |
| near romdata | NC | CNEARROM | MOD_9_NC |
| far romdata | FC | CFARROM | MOD_10_FC |
| huge romdata | HC | CHUGEROM | MOD_11_HC |
| shuge romdata | XC | CSHUGEROM | MOD_12_XC |
| int. ram data | IR | CIRAM | MOD_14_IR |
NOTE: You can NOT change the attributes of initialized Ramdata sections. Therefore, you can only use '#pragma combine' for constant initialized variables, and not for normal initialized variables.
When you take a look at the compiled output file (*.src) you can find the section name where the variables or code belongs to. For example, variable 'char row[100]' and 'char *p' in test.c are put in section 'TEST_1_NB' as you can see in test.src:
test.c
Section TEST_1_NB from test.src
The last two characters of the section name (NB) are referring to the memory code 'near data', see the table above. You can specify the absolute address of this 'near data' section, e.g. 0x28000, as follows:
test.c
Section TEST_1_NB from test.src
By adding #pragma default_attributes, the compiler will return to its default attributes, that means the absolute code section will end. Although you may declare variables of different type after #pragma combine (e.g. far, huge, system data etc.), the memory code NB specifies that only 'near data' variables will be affected! For more information, please refer to the compiler manual, chapter 3.2.2. "Section Allocation".
I have some external routines at fixed addresses. How can I call these routines from within my application?
There are two options:
Use the ASSIGN linker/locator control to resolve the function symbols at link time. This is the preferred method since it does not add pointer indirection overhead. See example #1.
Call the external functions via function pointers which were initialized for the correct addresses. See example #2.
In both cases, please note that you should avoid to locate anything in the address range of the external routines by filling in reserved memory ranges in EDE or using the linker control RESERVE.

Example #1
In our source file, we declare external functions extfa() and extfb():
In the link stage we link the external functions to their fixed addresses and reserve the memory range where the external functions reside. You can specify this in the Linker/Locator dialog box under the Reserve Tab. Please note that you always have to add a leading underscore when referring to a C-source symbol in the linker.
| Description | Mem Code |
|---|---|
| Flat Interrupt Concept | ASSIGN(_name(addr),...) |
| Task Concept | -Wl"ASSIGN(_name(addr),...)" |
Example #2
In your C source, define constant entry points, casted to pointers. Such constants can then be assigned to function pointers, through which the routines can be called:
I want to exchange data with an external source, but the problem is that floating point values are passed as little-endian (reverse storage order). How can I set things right in my program?
TASKING uses the IEEE-754 format for floating point variables. However, others may use the IEEE-754 little-endian format. Here is an example program to reverse the order of storage by means of a union.
EXAMPLE:
How can I avoid my non-initialized variables to be cleared at startup?
By default non-initialized static/public variables are cleared by the startup code which is linked to your application. To avoid this, you have some options:
- Define these variables in a separate C module and switch off the option for clearing non-initialized data. In EDE you can do this under the Allocation of Variables Tab in the C Compiler menu. On the command line, use the C166 option -Ob.
- Enclose these variable definitions by the lines "#pragma noclear" and "#pragma clear". C166 will omit these data sections, when building the C166_BSS section.
- Use inline assembly to allocate the special variables in a special data section (NOT used by other C variables).
- Make a separate assembly module, containing the allocation of these variables in a special data section.
I am using a C167CR and wondering why the CAN-registers are not defined in the register definition files. Can I simply add these definitions?
No, you should not add CAN definitions to the register definition files. CAN registers should be declared/defined as memory-mapped devices. This is because unlike SFRs, the CAN registers are not located in SFR or ESFR space and thus cannot be short-addressed (8-bit addressing). Since the CAN-registers are not SFR/ESFR registers, they should not be defined in files ETC\REG167*.DEF.
Definitions and declarations for the integrated CAN-controller can be found in the directory C166\EXAMPLES\CAN. The source files in this directory can be used as a starting point for using CAN in your application.
Why is there a user stack and a system stack? What do I need to know about these stacks?
The C166/ST10 controller and its derivatives supports two types of stacks.
- The system stack can be regarded as a processor stack which is implicitly used by the controller on instructions like CALL, RET, PUSH, and POP. This stack is located in internal memory. Its size may vary from 64 bytes up to 1 kb or 2 kb, but its high address is always fixed at 00FC00h. The system stack pointer SP is missing common stack addressing modes like pre/post- incr/decrement indirect addressing.
- The user stack is a mechanism used by the C-compiler for storing and passing on data. The compiler dedicates the general-purpose register R0 as a user stack pointer. When you divide your application into tasks, you can choose for each task to have its own user stack.
The is a basic idea of the C166 microcontroller design is a task-oriented architecture providing the ability to create task specific data stacks and to off-load data from the system stack. In many realtime-kernel implementations for the C166, the kernel owns the system stack and uses it for task-switching, while the application tasks only use the user stack.
Can I change the user stack size, and how can I do that?
The size of the C166 user stack is set by the linker/locator. It is an accumulation of the stack sections (named C166_US) generated by the compiler for each function. This is a worst case approach, so you will often end up with a stack size which is actually too large since the running application will never have all its functions active simultaneously. On the other hand, a stack size may have to be increased in a heavily recursive application.
Currently the only way to detect the amount of stack size used by your application is filling the entire user stack section with a byte pattern before running the application. Afterwards, you can dump the stack area and check how large the overwritten portion is. Once you have determined the stacksize actually needed, you can resize the stack in the Project Options | Linker/Locator | Stack and Heap dialog box. When using the command line interface, you need to use the following locator control:
SECSIZE( C166_US( size ) )
where size can be an absolute value (1000h) or a value relative to the original size (-200h, +5000). When using Flat Interrupt Concept (linking and locating in a single phase), the control only affects the preceding object module. To resize the user stack for the whole application, make sure the SECSIZE control is listed after the GENERAL control in the invocation. By default, the locator will issue a warning W 176 when a section size is decreased. You can suppress this warning using the control NOWARNING(176).
Can I change the system stack size, and how can I do that?
By default, the START.ASM startup module sets the system stack size to 256 words, i.e. the STKSZ bits in the SYSCON register are set to zero. To change the system stack size, select the dialog box Project Options | Linker/Locator | Stack and Heap and change the system stack size by using the select box.
Without having to change any runtime code, you can also set the system stack size at locate time using the control:
RESERVE SYSSTACK( num )
Num indicates the new value of for these bitfield. This control will set the initial values for SP, STKOV and STKUN. However, it will not affect the actual STKSZ bitfield in the SYSCON register.
Using the HEAPSIZE control seems to have no effect.
The linker/locator creates a ?C166_HEAP section when it resolves the special external symbols ?C166_HEAP_TOP or ?C166_HEAP_BOTTOM which are both used in the dynamic memory allocation functions (malloc, calloc, etc.). The size of the created section depends on the HEAPSIZE control. This means that when the symbols are resolved by the linker you have to specify the HEAPSIZE in the linker invocation. This way it is possible that each task in the Task Concept gets its own heap, which implies that no re-entrancy problems exist in the memory allocation functions. When using the Flat Interrupt Concept, the linker is not used and the symbols remain unresolved at locate time. The locator now resolves the symbols and creates the heap section with a size indicated by the HEAPSIZE control.
Conclusion: When using the Flat Interrupt Concept you should use the HEAPSIZE control at locate time. When using the Task Concept you should use the HEAPSIZE control at link time.
If I define a far or huge character pointer and initialize it with a string constant, the compiler still puts the string constant in a normal data section. Is this a compiler problem?
EXAMPLE when using small model:
You might expect the compiler to put that string into a far or huge section, respectively.
EXAMPLE:
However, it does not:
A string literal is always allocated in a normal section. In a variable definition the near, far or huge keyword only affects the variable itself, and not the initializer. In order to have your strings allocated in the type of section that you want, you should use the keyword in a character array definition. When initializing your character pointers, refer to the already defined character arrays.
EXAMPLE:
I have trouble running your C166/ST10 (evaluation) package. It seems to run software from other tool suppliers. Can you tell me what is wrong?
n case you have other (i.e. non-TASKING) C166 development tools installed on your PC, you might encounter problems running the TASKING C166/ST10 demo. Some other tools tend to change the DOS PATH settings in a way that the system first searches in the directory of these tools, so even before the DOS or WINDOWS directories! If you do have these tools installed, please check your PATH settings and correct them if necessary.
You can (temporarily) remove the PATH settings to the other tools (e.g. C:\C166EVAL\BIN) or put the settings for the TASKING tools (default to C:\DC166\BIN) before the settings for the non-TASKING tools.
I want to minimize interrupt latency by using '#pragma noframe' in my interrupt routines. Can I safely omit the saving and restoring of the DPP0 and DPP2 registers?
Currently, when compiling for small model and not accessing any far/huge data in your application, you can safely assume that DPP0 and DPP2 will never change at runtime. Hence, saving/restoring these registers on an interrupt is redundant and you can use '#pragma noframe' to suppress the compiler-generated interrupt prologue/epilogue.
However, when you do have far/huge data, there is no guarantee that DPP0 and DPP2 will remain untouched at runtime. The extended instruction set contains instructions for temporarily overriding pages and segments. Even when the extended instruction set is enabled, the compiler might generate code which touches DPP0 at runtime.
Furthermore, the compiler might generate code with calls to runtime library routines which touch DPP0 and/or DPP2. These are routines for moving/copying data among near/far/huge memory:
cpffb cpffw cpfhb cpfhw cpfnb cpfnw cphfb cphfw cphhb cphhw cphnb cphnw cpnfb cpnfw cpnhb cpnhw
Conclusion: To be safe, you are suggested not to minimize your interrupt frame when accessing far or huge data in your application.
I am getting multiple warnings "W118: unresolved symbol" when building my C++ project. Can I safely ignore these warnings?
W118 during the first link stage is normal behavior for a C++ project and nothing to worry about. If you add option -v to the control program (go to the dialog box Project Options | Linker/Locator | Miscellaneous and fill in -v at the field Additional Command Line Options), the output window will show you the two link stages explicitly.
You can suppress the warning by selecting the dialog box Project Options | Linker/Locator | Diagnostics and fill in: 118 at the field Display all warnings, except:.
My CAN application does not work anymore after using the C167CR GA or JA Step. Why?
Bit SYSCON.2 has been modified into a general XBUS Peripheral Enable bit, i.e. it controls both the XRAM and the CAN module:
"When bit SYSCON.2 = 0 (default after reset), and an access to an address in the range EF00h...EFFFh is made, either an external bus access is performed (if an external bus is enabled), or the Illegal Bus Trap is entered. In previous versions, the CAN module was accessed in this case."
For more information, please refer to Infineon's C167CR Errata Sheet from November 2, 2000 / Release 1.1 Stepping Code / Marking: ES-GA, GA, GA-T or ES-JA.
To set bit SYSCON.2 in the startup code, open the dialog box Project Options | Application | Startup, select register SYSCON and enable bit #2 (XPEN).