-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathnotes.txt
210 lines (178 loc) · 7.68 KB
/
notes.txt
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
+ DPRAM
http://search.digikey.com/scripts/DkSearch/dksus.dll?Detail&name=428-2156-ND
+ Documentation
http://www.atmel.com/dyn/products/app_notes.asp?part_id=4085
http://www.avrfreaks.net/wiki/index.php/Documentation:NGW
+ Buildroot 2.3.0
appliquer la patch à la fin de http://patchwork.kernel.org/patch/11166/ à
toolchain_build_avr32/linux-2.6.27.6/scripts/unifdef.c
puis
toolchain_build_avr32/uClibc-0.9.30/extra/scripts/unifdef.c
+ AVR32 atngw100
board setup code dans arch/avr32/boards/atngw100/setup.c
console: 115200,8,N,1
++ MAC address
http://www.avrfreaks.net/wiki/index.php/Documentation:NGW/NGW100_Ethernet_PHY
u-boot> setenv ethaddr XX:XX:XX:XX:XX:XX
u-boot> setenv eth1addr XX:XX:XX:XX:XX:XX
u-boot> saveenv
sn:936 (cf noir, 2 headers)
wan(eth_0) 00:04:25:1C:07:50
lan(eth_1) 00:04:25:1C:07:51
sn:6238 (cf bleu, 3 headers)
wan(eth_0) 00:04:25:1C:30:BC
lan(eth_1) 00:04:25:1C:30:BD
++ Boot from SD
http://www.avrfreaks.net/wiki/index.php/Documentation:AVR32_Linux_Development/Programming_an_SD_card_with_the_AVR32_Linux_file_system
http://www.avrfreaks.net/wiki/index.php/Documentation:NGW/Newbie/boot_from_SD
mkfs.ext2 -I 128 /dev/sdx1
tar -x [...]
vi etc/fstab
Uboot> askenv bootcmd
Please enter 'bootcmd':mmcinit; ext2load mmc 0:1 0x10400000 /boot/uImage; bootm
Uboot> set bootargs 'console=ttyS0 root=/dev/mmcblk0p1 rootwait'
Uboot> saveenv
Uboot> boot
++ Boot from flash
http://www.avrfreaks.net/wiki/index.php/Documentation:NGW/Newbie/boot_from_flash
Uboot> askenv bootcmd
Please enter 'bootcmd':fsload boot/uImage;bootm
Uboot> set bootargs 'console=ttyS0 root=/dev/mtdblock1 rootfstype=jffs2'
Uboot> saveenv
Uboot> boot
++ Firmware upgrade
http://www.avrfreaks.net/wiki/index.php/Documentation:NGW/Firmware_upgrade
avr32program erase -fcfi@0
avr32program program -F bin -vfcfi@0 uboot.bin
avr32program program -F bin -vfcfi@0 -O 0x20000 ngw_jffs2_root.img
++ GPIO direct access
GPIO_PIN_PB(N)= 32 + N
gpio_set_value(unsigned int gpio, int value)
+ __gpio_set_value(gpio, value)
chip = gpio_to_chip(gpio);
chip->set(chip, gpio - chip->base, value)
== set_pin_state(struct gpio_chip *chip, unsigned int offset, int high)
struct atmel_gpio_chip *gpio = to_atmel_gpio_chip(chip);
u32 mask = 1 << offset;
if (high)
gpio_writel(gpio, OVRS, mask);
else
gpio_writel(gpio, OVRC, mask);
+ #define gpio_writel(bank, reg, value) __raw_writel(value, &__gpio_regs(bank)->reg)
#define __gpio_regs(bank) ((struct gpio_regs __iomem *)(bank)->regs)
+ __raw_writel(u32 v, volatile void __iomem *addr)
gpio_writel(bank, reg, value) __raw_writel(value, &((struct gpio_regs __iomem *)(bank)->regs)->reg)
gpio_dev[pin >> 5]
static struct resource gpio_resource[] = {
PBMEM(0xffd02000)
regs = platform_get_resource(pdev, IORESOURCE_MEM, 0);
iomem_base = (void __iomem __force *)regs->start
chip->regs = 0xffd02000 + ((pin >> 5) * 0x200);
donc:
__raw_writel(value, chip->regs + offsetof(gpio_regs, OVR))
== analyse 2
GPIO_PIN_PB(N)= 32 + N
gpio_set_value(unsigned int gpio, int value)
+ __gpio_set_value(gpio, value)
chip = gpio_to_chip(gpio);
chip->set(chip, gpio - chip->base, value)
== gpio_set(struct gpio_chip *chip, unsigned offset, int value)
+ #define pio_writel(port,reg,value) __raw_writel((value), (port)->regs + PIO_##reg)
static struct resource pio0_resource[] = {
PBMEM(0xffe02800)
+ Kernel
pour voir les codes d'erreurs, chercher la définition de EINVAL (dans
include/asm-generic/errno-base.h)
struct file* filp; représente un open file descriptor
struct inode* inode; représente un fichier (sur disque, dans le vfs)
Il n'est pas permis de générer des page faults dans le kernel. S'il y en a ça
résulte en un oops.
Exemple d'un device qui utilise les GPIO, qui est un platform device et une
autre classe (input dans ce cas): drivers/input/keyboard/gpio_keys.c
Exemple d'utilisation des GPIO
drivers/leds/leds-gpio.c
+ GPIO
#include <include/asm/gpio.h>
Documentation/gpio.txt
++ particularités atmel
#include <mach/at32ap700x.h>
#include <mach/portmux.h>
at32_select_gpio(unsigned int pin, unsigned long flags)
pin: GPIO_PIN_PB(0), ...
flags: AT32_GPIOF_OUTPUT
+ Interface
un seul peut ouvrir en écriture, les autres bloquent ou fail avec Device Busy
autant que l'on veut peuvent ouvrir en lecture
+ Ledfloor
convertir et afficher une image:
convert test.png -resize 48x24 RGB:- | display -depth 8 -size 48x24 -sample
480 RGB:-
+ Todo
* retirer les ifdef de plateforme x86
* adaptation de blinkenlights pour utiliser le driver mplayer
* faire un vrai framebuffer device (pas vraiment utile)
* paramétrer la taille de l'écran
* par une option module
* par des ioctl
* en écrivant/lisant une structure avec plus d'information
* race condition dans l'io s'il y a lecture d'un frame et écriture par dessus
d'un nouveau frame
* une seule ouverture en écriture
* pouvoir lire la valeur du frame limiter à partir de /sys
* et la paramétrer (par un define et option module) comme un genre de
vsync
* implanter fsync pour que l'application puisse attendre que le frame ait été
"clocké" avant d'écrire le prochain frame
LDD p.166 "Never make a write call wait for data transmission before
returning"
pour la fonction de timing, voir qu'est-ce que .udelay fait dans
i2c_gpio_platform_data
* blank lors du unload
* option module, ioctl et fichier sys pour rotate
* utiliser epoll et des pipes (pour splice) dans lfserver
* supporter plusieurs client de ctl dans lfserver
* contrôle du blank..?
* détecter le packet loss (netstat -su, ou avec des numeros de séquence
ajoutés à la fin du frame et modifier lfdemo pour pouvoir ajuster le frame
rate
* ./lfdisplay -vl 192.168.1.2 -vr 192.168.1.3 test.png
* nouvelle image de boot
* correction gamma
* lfdemo sélectionne avec 1234.. black, white, red, green, blue, gamma, plasma
qa,sw,ed {increase, decrease} {frame rate limiter sur le client, latch
ndelay, clock ndelay} affiche le frame rate atteint (raffraîchi à chaque
seconde) envoi des numéros de frame
* lfserver
configure latch et clock delay avec ioctl
-b background,
sinon en mode verbose, affiche le frame rate (raffraîchi de la même façon)
et affiche le packet loss s'il y a des numéros de frame
* pour configurer les lignes, donner le numéro de banque du port et le numéro
de chaque pins, pour pas pouvoir configurer des pins sur deux ports
différents
* pouvoir configurer avec ioctl un délai de clock et de latch, utiliser la
fonction de délai
+ TooDone
* driver char-dev dans lequel on peut écrire 24 rangées * 48 colonnes * 3
couleurs * 8 bits
* changer les gpio lorsque l'on vient d'écrire cela
* code pour créer le device node (avec device_create,
http://kerneltrap.org/node/16688)
* programme pour convertir raw RGB <-> format nécessaire pour le sortir
* intégrer ces changements dans le driver pour plus de simplicité. Il
s'agit seulement de changer l'ordre de lecture dans le buffer et il
s'agit de quelquechose de spécifique à ce device, un autre ledfloor
serait peut-être implanté différement.
* io bloquant et non bloquant:
Avoir une waitqueue wq et un numéro de frame fnum
Lecture bloquante, wait_event_interruptible(wa, fnum != i), lire un frame
Lecture non bloquante, lire un frame
Écriture toujours "non-bloquante", prend du temps lorsque le frame est
complet et doit être écrit sur les gpio, fnum++, wake_up_interruptible(wq)
* déplacer ledfloor.h et le code pour registerer le device dans le même
répertoire que <mach/at32ap700x.h> et dans le board setup code
* programme d'affichage ncurses de ce qui devrait être sur l'écran
* faire que le platform register soit dans le module, pas besoin d'un kernel
custom
* renverser l'ordre des lignes
* réorganiser le driver pour tenir compte d'une clock longue