arm-linux-gcc linking problem

Hello,

In my source code, I try to define a two dimensions array, but error occures when trying to link the objects files together. It says undefined reference to memcpy. I do not call the memcpy function in my array definition. Although I add #include <memory.h> or #include <string.h> at the beginning of my source code, it does not work.

Anyone knows how to solve the problem? Thanks!

Regards,

Kevin Zhu

We need more info.

Code fragments where you define the arrays, how do you compile and link ?

Makefile ?

Regards,

Magnus

Without seeing the code it’s hard to tell what the problem is, but I have gotten this error before when I tried to initialize an array like this:

int array[3] = {0, 0, 0};

Like mlu said, it will be much more helpful to see your code.

right, doing that initialization actually translates into a memcpy or memset, so if your linking for the standard c library stuff isn’t working, it will result in a copile error.

Here’s the code. And all the strings like REG_PCLK_FREQ_RATIO_0 are defined macros, whose values are commented at the end of each line. The compiler said:“undefined reference to memcpy.” at this line “unsigned long lcd_hw_init[2]”.

unsigned long lcd_hw_init[2]=

{

{REG_PCLK_FREQ_RATIO_0 ,0xff},//0x158

{REG_PCLK_FREQ_RATIO_1 ,0xff},//0x159

{REG_PCLK_FREQ_RATIO_2 ,0x00},//0x15a

{REG_PANEL_TYPE ,0x72},//0x10 /serial tft/

{REG_MOD_RATE ,0x00},//0x11

{REG_HORIZ_TOTAL_0 ,0x18},//0x12

{REG_HORIZ_TOTAL_1 ,0x07},//0x13

{REG_HDP ,0x15},//0x14

{REG_HDP_START_POS0 ,0x0a},//0x16

{REG_HDP_START_POS1 ,0x00},//0x17

{REG_VERT_TOTAL0 ,0xef},//0x18

{REG_VERT_TOTAL1 ,0x00},//0x19

{REG_VDP0 ,0xdb},//0x1C

{REG_VDP1 ,0x00},//0x1D

{REG_VDP_START_POS0 ,0x03},//0x1e

{REG_VDP_START_POS1 ,0x00},//0x1f

{REG_HSYNC_PULSE_WIDTH ,0x81},//0x20

{REG_HSYNC_PULSE_START_POS0 ,0x00},//0x22

{REG_HSYNC_PULSE_START_POS1 ,0x00},//0x23

{REG_VSYNC_PULSE_WIDTH ,0x80},//0x24

{REG_VSYNC_PULSE_START_POS0 ,0x00},//0x26

{REG_VSYNC_PULSE_START_POS1 ,0x00},//0x27

{REG_GPIO_STATUS_CONTROL1 ,0x00},//0xac

{REG_HRTFT_SPECIAL_OUTPUT ,0x01},//0x38

{REG_DISPLAY_MODE ,0xC4},//0x70//default off

{REG_DV_OFORMAT ,0x00},//0x1a4

{REG_HORIZ_TOTAL_0 ,0x15},//0x12

{REG_HORIZ_TOTAL_1 ,0x07},//0x13

{REG_HDP ,0x13},//0x14

{REG_HDP_START_POS0 ,0x04},//0x16

{REG_VERT_TOTAL0 ,240},//0x18

{REG_VDP0 ,239},//0x1c

{REG_VDP_START_POS0 ,0},//0x1e

{REG_FPFRAME_START_OFFSET0 ,1},//0x30

{REG_HSYNC_PULSE_START_POS0 ,1},//0x22

// {REG_DV_FRAME_SAMPLING, 0x01},//0x161

{REG_LLINE_PULSE_START_SUBPIXEL_POS, 0x03},//0x21=3pixels

{REG_LCD_SUBPIXEL_ALIGNMENT, 0x04},//0x42=BRG/RGB

// {REG_DV_SUBPIXEL_MODE, 0x02},

//0x1a5=enable subpixel accurate horizontal decimation in DV and set “1st row inside,2nd row outside”=0x02

{REG_DEFINE_END ,0x00}//0xFFFF

};

Here’s my Makefile.

OBJECTS = startup.o target.o UART0.o keypad.o k9f2808.o flash.o armvic.o au030.o test.o io.o

CC = arm-linux-gcc -v

LD = arm-linux-ld -v

AR = arm-linux-ar -v

AS = arm-linux-as -v

CP = arm-linux-objcopy

OD = arm-linux-objdump

CFLAG = -I./ -c -fno-common -O2 -g

AFLAG = -ahls -mapcs-32 -o startup.o

LFLAG = -Map boot.map -T link.lds

HEXFORMAT = -O ihex

BINFORMAT = -O binary

ODFLAG = -x --syms

all: test

test: boot.out

@ echo “Copying…”

$(CP) $(HEXFORMAT) boot.out boot.hex

$(CP) $(BINFORMAT) boot.out boot.bin

$(OD) $(ODFLAG) boot.out > boot.dmp

boot.out: $(OBJECTS) link.lds

@ echo “Linking…”

$(LD) $(LFLAG) $(OBJECTS) -o boot.out

$(LD) $(LFLAG) $(OBJECTS) -o boot.elf

startup.o: startup.S

@echo “Assembling…”

$(AS) $(AFLAG) startup.S > startup.lst

%.o: %.c

@echo “Compiling…”

$(CC) $(CFLAG) $<

clean:

rm -f *.o *.elf *.bin *.hex *.lst *.dmp *.map *.elf *.out

Regards,

Kevin

For one thing, why don’t you specify the length of the first array dimension? I don’t even see how that compiles unless GCC assumes its value to be 1 or some other default. If it is 1, then you haven’t really gained anything in using a 2-dimensional array as opposed to a 1-dimensional array; in fact, you would only have a 2 variable long array! I would try doing this first and seeing if it fixes the error (make sure that your initialization stuff and the array dimensions have the EXACT same length or GCC will complain).

If this doesn’t work, chances are your error is the same as the one I described above. To fix it, simply declare the array without any initialization. Then you will have to assign each variable of the array separately.

Hi,

I think the problem is the linker can not find the definition of the function, it only finds the prototype. That’s why there’s no error while compiling, but linking. I am sure there are some mistakes with my Makefile, but I don’t know what they are. Some say I should add some directory to the LD_LIBRARY_PATH, however, I can’t find it.

Besides this problem, I also met “undefined reference to __divis3” at where I use the divider. (e.g. 32/variable).

Though I have add -lm -lc to my Makefile in the linking options, it did not work.

Is there something wrong with my cygwin or something else?

Regards,

Kevin

I had simalar problems getting the Library files to link in.

Check out this thread for more :-

http://en.mikrocontroller.net/topic/64975#new

Good Luck!

You are correct that it can’t find the definition of the function memcpy, but if you initialize your array like I am suggesting, you won’t need it. I have found it easier to avoid the memory-related functions in my project (such as memcpy, malloc, and free) unless I could not do what I’m doing without them. I still think you should put in both array indices, though.

As far as your error pointing to __divis3, if you link in libgcc.a, you will clear that up. Jim Lynch wrote a short tutorial on it that has been discussed on this forum, so a quick search should turn it up (you can probably search for libgcc.a and find it).