一.修改平台輸入時鐘和機器碼
修改核心源碼arch/arm/mach-s3c2440/mach-smdk2440.c” 檔案的大概162行或163行,把16.9344MHz改為12MHz,因為TQ2440使用的就是12MHz的外部時鐘源輸入,即把16934400改為12000000。
在TQ2440使用的uboot中設定了機器碼為168,是以核心這裡需要修改機器碼,否則會
出現不能啟動的情況。機器碼儲存在核心源碼的“arch/arm/tools/mach-types”檔案中,在大概379行,把
原來的362改為168儲存即可。
二.利用預設配置單做配置單
#make menuconfig ARCH=arm CROSS_COMPILE=arm-linux-
在“Load an Alternate Configuration File”回車,輸入arch/arm/configs/s3c2410_defconfig,點OK
然後傳回到配置界面,進入到“SystemType”選項下的配置單:

然後配置各個平台如下所示
SystemType --->
S3C2410Machines --->
[*]SMDK2410/A9M2410
[]IPAQH1940
[]AcerN30
[]SimtecElectronicsBAST(EB2410ITX)
[]NexVisionOTOMBoard
[]AMLM5900Series
[]ThorcomVR1000
[]QT2410
S3C2412Machines --->
[]SMDK2413
[]SMDK2412
[]VMSTMS
S3C2440Machines --->
[]SimtecElectronicsANUBIS
[]SimtecIM2440D20(OSIRIS) module
[]HPiPAQrx3715 [*]SMDK2440
[]NexVisionNEXCODER2440LightBoard
[*]SMDK2440withS3C2440CPUmodule
S3C2442Machines --->
[]SMDM2440withS3C2442CPUmodule
S3C2443Machines --->
[]SMDK2443
配置完畢這個地方後,退回到最初的配置單。
在配置單中添加自己的資訊
然後配置選項,配置如下
(Generalsetup --->
[*]Promptfordevelopmentand/orincompletecode/drivers
(-EmbedSky)Localversion-appendtokernelrelease
[*]SystemVIPC
(17)Kernellogbuffersize(16=>64KB,17=>128KB)
-*-Namespacessupport
ChooseSLABallocator(SLUB(UnqueuedAllocator)) --->
選擇是否支援EEAABBII
然後對是否支援EABI進行選擇,配置如下:
KernelFeatures --->
Memorysplit(3G/1Guser/kernelsplit) --->
[]PreemptibleKernel(EXPERIMENTAL)
[*]UsetheARMEABItocompilethekernel
[*] AllowoldABIbinariestorunwiththiskernel(EXPERIMENTAL)
[]HighMemory Support(EXPERIMENTAL)
Memorymodel(FlatMemory) --->
[]AddLRUlisttotracknon-evictablepages
(4096)Lowaddressspacetoprotectfromuserallocation
說明:如果您使用的4.3.3的編譯器(也就是支出EABI 的編譯器),
那麼就選中它;如果您使用3.4.5或以下的編譯器,那麼就不要選中它。
然後儲存自己的配置單為.config
三.Nand Flash 驅動移植
修改核心源碼“arch/arm/plat-s3c24xx/common-smdk.c”檔案,在109 行左右,有一個結構體名為:
smdk_default_nand_part[],将其修改為如下清單所示:
staticstructmtd_partitionsmdk_default_nand_part[]={
[0]={
.name ="EmbedSky_Board_uboot",
.offset =0x00000000,
.size =0x00040000,
},
[1]={
.name ="EmbedSky_Board_kernel",
.offset =0x00200000,
.size =0x00300000,
},
[2]={
.name ="EmbedSky_Board_yaffs2",
.offset =0x00500000,
.size =MTDPART_SIZ_FULL
}
};
然後修改NandFlash 的讀寫比對時間,修改common-smdk.c 檔案的剛剛修改後的大概140行左右的
smdk_nand_info結構體,修改内容如下:(這個步驟可以不用做)
staticstructs3c2410_platform_nandsmdk_nand_info={
.tacls =10,
.twrph0 =25,
.twrph1 =10,
.nr_sets =ARRAY_SIZE(smdk_nand_sets),
.sets =smdk_nand_sets,
};
然後修改“drivers/mtd/nand/s3c2410.c”檔案的752行,将原來的内容改為如下所示:
chip->ecc.mode =NAND_ECC_NONE; //NAND_ECC_SOFT;
然後需要在剛剛完成的配置單中添加上對NandFlash支援的配置選項,輸入:#make menuconfig ARCH=arm CROSS_COMPILE=arm-linux-,進入配置單選項,然後配置如下所示:
DeviceDrivers --->
<*>MemoryTechnologyDevice(MTD)support --->
[*] MTDpartitioningsupport
<> RedBootpartitiontableparsing
[] Commandlinepartitiontableparsing
<*> DirectchardeviceaccesstoMTDdevices
-*- CommoninterfacetoblocklayerforMTD'translationlayers
<*> CachingblockdeviceaccesstoMTDdevices
<*> NANDDeviceSupport --->
<*> NANDFlashsupportforS3C2410/S3C2440SoC
[] S3C2410NANDHardwareECC
配置完畢這些之後,儲存配置單。
注:現在已經可以編譯核心下載下傳到闆子裡了,但是還不支援網卡,TQ2440上的網卡是dm9000.
四.dm9000網卡驅動移植
修改核心源碼的“arch/arm/mach-s3c2440/mach-smdk2440.c”檔案:
在50行添加頭檔案内容如下;
#include<linux/dm9000.h>
在154行添加如下内容所示:
staticstructs3c2410fb_mach_infotq2440_fb_info__initdata={
.displays =&tq2440_lcd_cfg,
.num_displays=1,
.default_display=0,
#if0
.gpccon =0xaa940659,
.gpccon_mask=0xffffffff,
.gpcup =0x0000ffff,
.gpcup_mask =0xffffffff,
.gpdcon =0xaa84aaa0,
.gpdcon_mask=0xffffffff,
.gpdup =0x0000faff,
.gpdup_mask =0xffffffff,
#endif
// .lpcsel =((0xCE6)&~7)|1<<4,
};
staticstructresources3c_dm9k_resource[]={
[0]={
.start=S3C2410_CS4,
.end =S3C2410_CS4+3,
.flags =IORESOURCE_MEM,
},
[1]={
.start=S3C2410_CS4+4,
.end =S3C2410_CS4+4+3,
.flags =IORESOURCE_MEM,
},
[2]={
.start=IRQ_EINT7,
.end =IRQ_EINT7,
.flags =IORESOURCE_IRQ|IRQF_TRIGGER_RISING,
}
};
staticstructdm9000_plat_datas3c_dm9k_platdata={
.flags =DM9000_PLATF_16BITONLY,
};
structplatform_devices3c_device_dm9000={
.name ="dm9000",
.id =0,
.num_resources =ARRAY_SIZE(s3c_dm9k_resource),
.resource =s3c_dm9k_resource,
.dev ={
.platform_data=&s3c_dm9k_platdata,
}
};
在191行添加如下内容所示:
staticstructplatform_device*smdk2440_devices[]__initdata={
&s3c_device_usb,
&s3c_device_lcd,
&s3c_device_wdt,
&s3c_device_i2c0,
&s3c_device_iis,
&s3c_device_dm9000,
};
在“drivers/net/dm9000.c”檔案中修改如下:
在41行添加的頭檔案内容如下:
#ifdefined(CONFIG_ARCH_S3C2410)
#include<mach/regs-mem.h>
#endif
在1194行添加内容如下所示:
int i;
u32 id_val;
#ifdefined(CONFIG_ARCH_S3C2410)
unsignedintoldval_bwscon=*(volatileunsignedint*)S3C2410_BWSCON;
unsignedintoldval_bankcon4=*(volatileunsignedint*)S3C2410_BANKCON4;
#endif
在1209行添加如下内容:
dev_dbg(&pdev ->dev,"dm9000_probe()\n");
#ifdefined(CONFIG_ARCH_S3C2410)
*((volatile unsigned int *)S3C2410_BWSCON) = (oldval_bwscon & ~(3<<16)) |
S3C2410_BWSCON_DW4_16|S3C2410_BWSCON_WS4|S3C2410_BWSCON_ST4;
*((volatileunsignedint*)S3C2410_BANKCON4)=0x1f7c;
#endif
修改1377行的内容如下所示:(主要是添加mac值)
#ifdefined(CONFIG_ARCH_S3C2410)
printk("NowusethedefaultMACaddress:10:23:45:67:89:ab\n");
mac_src="EmbedSky";
ndev->dev_addr[0]=0x10;
ndev->dev_addr[1]=0x23;
ndev->dev_addr[2]=0x45;
ndev->dev_addr[3]=0x67;
ndev->dev_addr[4]=0x89;
ndev->dev_addr[5]=0xab;
#else
mac_src="eeprom";
for(i=0;i<6;i+=2)
dm9000_read_eeprom(db,i/2,ndev->dev_addr+i);
if(!is_valid_ether_addr(ndev->dev_addr)&&pdata!=NULL){
mac_src="platformdata";
memcpy(ndev->dev_addr,pdata->dev_addr,6);
}
if(!is_valid_ether_addr(ndev->dev_addr)){
mac_src="chip";
for(i=0;i<6;i++)
ndev->dev_addr[i]=ior(db,i+DM9000_PAR);
}
if(!is_valid_ether_addr(ndev->dev_addr))
dev_warn(db->dev,"%s:InvalidethernetMACaddress.Please"
"setusingifconfig\n",ndev->name);
#endif
在1423行添加如下内容:
out:
#ifdefined(CONFIG_ARCH_S3C2410)
*(volatileunsignedint*)S3C2410_BWSCON =oldval_bwscon;
*(volatileunsignedint*)S3C2410_BANKCON4=oldval_bankcon4;
#endif
修改完以上的内容之後,進入配置單,然後添加上對DM9000網卡的配置:
[*]Networkingsupport --->
---Networkingsupport
Networkingoptions --->
<>Packetsocket
<*>Unixdomainsockets
<>PF_KEYsockets
[*]TCP/IPnetworking
[] IP:multicasting
[] IP:advancedrouter
[*] IP:kernellevelautoconfiguration
[*] IP:DHCPsupport
[] IP:BOOTPsupport
[] IP:RARPsupport
DeviceDrivers --->
[*]Networkdevicesupport --->
[*] Ethernet(10or100Mbit) --->
-*- GenericMediaIndependentInterfacedevicesupport
<*> DM9000support
(4) DM9000maximumdebuglevel
配置好後,儲存配置單。
如果想要測試一下,編譯核心,燒入開發版運作
#make uImage ARCH=arm CROSS_COMPILE=arm-linux-
編譯完成後uImage在arch/arm/boot/裡。
五.LCD(W43)驅動移植
修改drivers/video/s3c210fb.c的371行:
staticvoids3c2410fb_activate_var(structfb_info*info)
{
structs3c2410fb_info*fbi=info->par;
void__iomem*regs=fbi->io;
inttype=fbi->regs.lcdcon1&S3C2410_LCDCON1_TFT;
structfb_var_screeninfo*var=&info->var;
structs3c2410fb_mach_info*mach_info=fbi->dev->platform_data;
structs3c2410fb_display*default_display=mach_info->displays+
mach_info->default_display;
intclkdiv=s3c2410fb_calc_pixclk(fbi,var->pixclock)/2;
dprintk("%s:var->xres =%d\n",__FUNCTION__,var->xres);
dprintk("%s:var->yres =%d\n",__FUNCTION__,var->yres);
dprintk("%s:var->bpp =%d\n",__FUNCTION__,var->bits_per_pixel);
if(type==S3C2410_LCDCON1_TFT){
s3c2410fb_calculate_tft_lcd_regs(info,&fbi->regs);
--clkdiv;
if(clkdiv<0)
clkdiv=0;
}else{
s3c2410fb_calculate_stn_lcd_regs(info,&fbi->regs);
if(clkdiv<2)
clkdiv=2;
}
然後修改第393行:
// fbi->regs.lcdcon1|= S3C2410_LCDCON1_CLKVAL(clkdiv);
fbi->regs.lcdcon1|= S3C2410_LCDCON1_CLKVAL(default_display->setclkval);
下面在structs3c2410fb_display結構體中加入setclkval變量,修改arch/arm/mach-s3c2410/include/mach/fb.h檔案(40行添加):
structs3c2410fb_display{
unsigned type;
unsigned shortwidth;
unsigned shortheight;
unsigned shortxres;
unsigned shortyres;
unsigned shortbpp;
unsigned pixclock;
unsigned setclkval;
unsigned shortleft_margin;
unsigned shortright_margin;
unsigned shorthsync_len;
unsigned shortupper_margin;
unsigned shortlower_margin;
unsigned shortvsync_len;
unsignedlong lcdcon5;
};
然後修改LCD各個參數的配置,該配置參數在“arch/arm/mach-s3c2440/mach-smdk2440.c”檔案中的
由107行開始的結構體中:
staticstructs3c2410fb_displaysmdk2440_lcd_cfg__initdata={
.lcdcon5 =S3C2410_LCDCON5_FRM565|
S3C2410_LCDCON5_INVVLINE|
S3C2410_LCDCON5_INVVFRAME|
S3C2410_LCDCON5_PWREN|
S3C2410_LCDCON5_HWSWP,
.type =S3C2410_LCDCON1_TFT,
.width =480,
.height =272,
.pixclock =40000,
.setclkval =0x4,
.xres =480,
.yres =272,
.bpp =16,
.left_margin =19,
.right_margin =10,
.hsync_len =30,
.upper_margin=4,
.lower_margin=2,
.vsync_len =8,
};
staticstructs3c2410fb_mach_infosmdk2440_fb_info__initdata={
.displays =&smdk2440_lcd_cfg,
.num_displays=1,
.default_display=0,
#if0
.gpccon =0xaa940659,
.gpccon_mask=0xffffffff,
.gpcup =0x0000ffff,
.gpcup_mask =0xffffffff,
.gpdcon =0xaa84aaa0,
.gpdcon_mask=0xffffffff,
.gpdup =0x0000faff,
.gpdup_mask =0xffffffff,
#endif
// .lpcsel =((0xCE6)&~7)|1<<4,
然後配置核心#make menuconfig ARCH=arm CROSS_COMPILE=arm-linux-:
Device Drivers --->
Graphics support --->
<*>Support for frame buffer devices --->
<*>S3C2410 LCD frame buffer support
儲存後編譯核心,燒入開發版運作。(注:啟動後開發闆的LCD為黑屏)
六.開機LOGO制作
找一張480x272的圖檔,然後用GIMP軟體将其打開,右鍵單擊圖檔彈出菜單選擇 Image->mode->Indexed 将Maximum number of colors改為224.右擊圖檔選擇File->save as寫完名稱logo_linux_clut224.ppm後save,會彈出對話框,選擇Ascii,然後save。這樣ppm圖像就做好了。
将做好的logo_linux_clut224.ppm圖像複制到drivers/video/logo中,然後删除掉logo_linux_clut224.c和logo_linux_clut224.o
做好上面步驟以後配置核心#make menuconfig ARCH=arm CROSS_COMPILE=arm-linux-:
Device Drivers --->
Graphics support --->
[*]Bootup logo --->
[*]Standart 224-color linux logo
儲存後編譯核心,燒入開發版運作。(啟動開發闆後你就能看到你的新logo圖檔了)
七.聲霸卡驅動的移植
修改arch/arm/mach/mach-s3c2440/mach-smdk2440.c檔案
添加頭檔案
#include<sound/s3c24xx_uda134x.h>
然後添加以下部分:
staticstructs3c24xx_uda134x_platform_datas3c24xx_uda134x_data={
.l3_clk=S3C2410_GPB4,
.l3_data=S3C2410_GPB3,
.l3_mode=S3C2410_GPB2,
.model=UDA134X_UDA1341,
};
staticstructplatform_devices3c_device_uda134x={
.name="s3c24xx_uda134x",
.dev={
.platform_data =&s3c24xx_uda134x_data,
}
};
staticstructplatform_device*smdk2440_devices[]__initdata={
&s3c_device_usb,
&s3c_device_lcd,
&s3c_device_wdt,
&s3c_device_i2c0,
&s3c_device_iis,
&s3c_device_rtc,
&s3c_device_uda134x,
};
然後配置核心:#make menuconfig ARCH=arm CROSS_COMPILE=arm-linux-:
DeviceDrivers --->
<*>Soundcardsupport --->
---Soundcardsupport
<*> AdvancedLinuxSoundArchitecture --->
---AdvancedLinuxSoundArchitecture
<*> OSSMixerAPI
<*> OSSPCM(digitalaudio)API
[*] Verboseprocfscontents
<*> ALSAforSoCaudiosupport --->
---ALSAforSoCaudiosupport
<*> SoCAudiofortheSamsungS3CXXXXchips
<*> SoCI2SAudiosupportUDA134Xwiredt
<*> Open Sound System (DEPRECATED) --->
儲存後編譯核心,燒入開發版運作。可以copy一個MP3檔案到NFS檔案系統中,然後用
#cat xxx.mp3 > /dev/dsp
如果聽到嘩嘩啦啦的聲音,就說明移植成功了!
八.SD卡驅動移植在
Linux-2.6.29的核心中隻需要添加SD裝置到裝置初始化清單中,修改核心源碼的“arch/arm/plat-
s3c24xx/common-smdk.c”檔案
staticstructplatform_device__initdata*smdk_devs[]={
&s3c_device_nand,
&s3c_device_sdi,
&smdk_led4,
&smdk_led5,
&smdk_led6,
&smdk_led7,
};
修改Linux-2.6.29核心源碼的“drivers/mmc/host/s3cmci.c”檔案,添加和開發闆相關的SD卡中斷處
理,在1335行添加如下内容(即修改s3cmci_probe函數):
host->irq_cd = s3c2410_gpio_getirq(host->pdata->gpio_detect);
host->irq_cd=IRQ_EINT16;
s3c2410_gpio_cfgpin(S3C2410_GPG8,S3C2410_GPG8_EINT16);
然後配置核心:
DeviceDrivers --->
<*>MMC/SD/SDIOcardsupport --->
---MMC/SD/SDIOcardsupport
***MMC/SD/SDIOCardDrivers***
<*> MMCblockdevicedriver
[*] Usebouncebufferforsimplehosts
***MMC/SD/SDIOHostControllerDrivers***
<*> SamsungS3CSD/MMCCardInterfacesupport
儲存後編譯核心,燒入開發版運作。
九.RTC驅動移植
在2.6.29上的實時時鐘驅動是非常完善,這裡隻需要添加到RTC裝置到裝置初始化清單中就行了。
修改核心源碼“arch/arm/mach-s3c2440/mach-smdk2440.c”檔案,在行添加如下内容:staticstructplatform_device*smdk2440_devices[]__initdata={
&s3c_device_usb,
&s3c_device_lcd,
&s3c_device_wdt,
&s3c_device_i2c,
&s3c_device_iis,
&s3c_device_rtc,
};
然後配置如下所示:
DeviceDrivers --->
<*>RealTimeClock --->
[*] SetsystemtimefromRTConstartupandresume
(rtc0) RTCusedtosetthesystemtime
[*] /sys/class/rtc/rtcN(sysfs)
[*] /proc/driver/rtc(procfsforrtc0)
[*] /dev/rtcN(characterdevices)
<*> SamsungS3CseriesSoCRTC
配置完畢後,編譯核心燒寫到開發闆中,然後使用busybox自帶的hwclock和date指令可以設定RTC,
$date -s 月日時分年 //其中月、日、時和分都是兩位數,年是四位數。
//比如:020416102009就是2009年2月4日16點10分
$hwclock -w //儲存剛剛設定的時鐘。
設定好之後關閉電源,實時時鐘依然會工作。為了讓系統啟動時能夠同步設定好的RTC,需要在
檔案系統的“/etc/init.d/rcS”檔案中添加一條RTC同步的指令,啟動後,系統就會自動同步RTC了。
下面是新的rcS檔案的内容:
#! /bin/sh
/bin/mount -a
/bin/mount -t tmpfs mdev /dev
/bin/echo /sbin/mdev > /proc/sys/kernel/hotplug
mdev -s
hwclock -s
十.USB驅動移植
其實2.6.29核心已經有完善的USB裝置驅動,我們隻需配置一下:
輸入:#make menuconfig ARCH=arm CROSS_COMPILE=arm-linux-,然後進入配置單,配置如下:
DeviceDrivers --->
SCSIdevicesupport --->
<*>SCSIdevicesupport
[*]legacy/proc/scsi/support
<*>SCSIdisksupport
<*>SCSICDROMsupport
[*]HIDDevices --->
<*> USBHumanInterfaceDevice(fullHID)support
[*] /dev/hiddevrawHIDdevicesupport
[*]USBsupport --->
<*> SupportforHost-sideUSB
[*] USBdevicefilesystem
[*] USBdeviceclass-devices(DEPRECATED)
<*> OHCIHCDsupport
<*> USBMassStoragesupport
然後編譯核心,燒入開發闆。輸入指令:
#mount /dev/sda1 /mnt/udisk
#ls /mnt/udisk
來測試驅動。
出錯
進入核心源碼目錄
vi arch/arm/include/asm/elf.h
修改
#define R_ARM_ABS32 2
#define R_ARM_CALL 28
#define R_ARM_JUMP24 29
#define R_ARM_V4BX 40
vi arch/arm/kernel/module.c
在apply_relocate函數中增加如下語句:
*(u32 *)loc |= offset & 0x00ffffff;
break;
+ case R_ARM_V4BX:
+
+ *(u32 *)loc &= 0xf000000f;
+ *(u32 *)loc |= 0x01a0f000;
+ break;
+
default:
printk(KERN_ERR "%s: unknown relocation: %u\n",
module->name, ELF32_R_TYPE(rel->r_info));