Sign in Join
Wiki copytemporary

Lazarus on Raspberry Pi/es: what changed

Revision 1 to 2. Removed lines have a minus sign; added lines have a plus sign.

OldNewLine
11La información que viene a continuación es una traducción lo más aproximada posible de la entrada en inglés (con alguna variación allí donde requiera ser más detallada o explicativa) y puede que las que se redacten en los otros idiomas alternativos de esta wiki. Cada uno que utilice esta información bajo su propio riesgo, puede contener errores. Antes de aplicar los ejemplos asegurarse que la información es aplicable (y se corresponde) con la placa sobre la que se va a trabajar dada la existencia de diferentes modelos en los cuales tanto los pines de conexión como su funcionalidad y voltaje pueden variar. Si no se tiene conocimiento de lo que se está haciendo mejor no aplicarlo. Por otro lado siempre que se trabaja con dispositivos electrónicos se deben guardar las medidas de seguridad apropiadas dado que un uso indebido de dicho hardware puede conllevar la pérdida de la garantía. Desde aquí no se dá garantía ni implícita ni explícita sobre el correcto funcionamiento de la información aquí mostrada. Antes de seguir este tutorial es recomendable tener conocimientos de electrónica (también para conocer los riesgos de manejar tensiones e intensidades), aunque los componentes empleados en los ejemplos son simples.
22
33<img src="Lazarus_on_Raspberry_Pi_Raspian_Wheezy_version_2012-10-28.png" title="Lazarus on Raspbian Wheezy" width="200" alt="Lazarus on Raspbian Wheezy" /> *(Raspberry Pi only)*
44
55**Raspberry Pi** es un ordenador con una placa del tamaño de una tarjeta de crédito (ver fotos más abajo). Ha sido diseñada en Reino Unido (UK) por la Fundación Raspberry Pi con la intención de fomentar el aprendizaje básico de la computación en escuelas. Las Raspberry Pi se utilizan también para propósitos tan diversos como pueden ser servidores de medios, robótica e ingeniería de control.
66
77La Fundación Raspberry Pi recomienda [[Raspbian]] Wheezy como la distribución estandar a utilizar con su hardware. También se utilizan sistemas alternativos tales como RISC y distribuciones Linux variadas y [[Android]].
88
99Lazarus corre en modo nativo bajo la distro Raspbian con sistema operativo Linux.
1010
1111## Installando y compilando Lazarus
1212
1313### Instalación simple bajo Raspbian
1414
1515#### Raspberry Pi 1
1616
1717En la distro de Linux Raspbian es fácil instalar Lazarus y FreePascal. Para lograrlo simplemente abre una ventana de terminal y teclea lo siguiente:
1818
1919``` bash
2020sudo apt-get update
2121sudo apt-get upgrade
2222sudo apt-get install fpc
2323sudo apt-get install lazarus
2424```
2525
2626Esto instala una versión precompilada estable de FreePascal y Lazarus en la distro Raspbian que corre en el hardware Raspberry Pi. Por supuesto se necesita una conexión de red. La instalación puede llevar unos 30 minutos, pero la mayor parte de este proceso tiene lugar automáticamente. Después de la instalación ya se puede arrancar Lazarus desde la sección "Programming" en el menú de comienzo de LXDE.
2727
2828Install Lazarus Rasbian Part1 en.png\|Paso instalación 1 Install Lazarus Rasbian Part2 en.png\|Paso instalación 2 Install Lazarus Rasbian Part3 en.png\|Paso instalación 3 Install Lazarus Rasbian Part4 en.png\|Paso instalación 4
2929
3030Si necesitas una versión más nueva, o si Lazarus/FreePascal muestran errores durante la instalación puedes consultar más información [aquí](http://www.raspberrypi.org/forums/viewtopic.php?f=34&t=88145).
3131
3232#### Raspberry Pi 2
3333
3434Desde junio de 2015 el método de instalación regular "out of the box (listo para usar)" también funciona para Raspberry Pi 2 Modelo B. La versión que lleva instalada es, por tanto, demasiado antigua. Para aquellos que busquen construir los últimos IDE de FreePascal y Lazarus mejor ver [este artículo](http://www.tweaking4all.com/hardware/raspberry-pi/install-lazarus-pascal-on-raspberry-pi-2/).
3535
3636<File:Lazarus> 0 9 30 4 on RPi 2.png\|Lazarus "out of the box" en Raspberry Pi 2
3737
3838160
3939
4040#### Raspberry Pi 3
4141
4242Ver Raspberry Pi 2.
4343
44-<figure>
45-<img src="RaspBerryPi3B+.png" title=" Foto detalle RaspBerry Pi 3 B+|thumb|220px|center" />
46-<figcaption> Foto detalle RaspBerry Pi 3 B+|thumb|220px|center</figcaption>
47-</figure>
44+![](/wiki-images/5/50/RaspBerryPi3B%2B.png)
4845
4946<File:RaspBerryPi3B+_img1.png>
5047
5148<File:RaspBerryPi3B+_img2.png>
5249
5350Como se puede observar tiene más pines de los cuales se debe consultar la funcionalidad de cada uno antes de conectar algo.
5451
55-<figure>
56-<img src="RaspBerryPi3B+_img3.png" title=" Foto detalle RaspBerry Pi 3 B+|thumb|220px|center" />
57-<figcaption> Foto detalle RaspBerry Pi 3 B+|thumb|220px|center</figcaption>
58-</figure>
52+![](/wiki-images/f/f3/RaspBerryPi3B%2B_img3.png)
5953
6054### Compilación cruzada (cross compiling) para Raspberry Pi desde Windows
6155
62561\. Utilizando fpcup
6357
6458Un camino es utilizar fpcup para configurar un compilador cruzado; seguir estas instrucciones:
6559
6660[[fpcup|fpcup#Linux_ARM_cross_compiler]]
6761
68622\. Utilizando scripts
6963
7064Alternativamente, para una aproximación más manual, y utilizando ficheros de proceso por lotes, puedes seguir los siguientes pasos.
7165
72662.1 Prerequisitos
7367
7468`FPC 2.7.1 or higher installed with sourcecode`\
7569`Install the Windows version from the Linaro binutils for linux gnueabihf into %FPCPATH%/bin/win32-armhf-linux `[`1`](https://launchpad.net/linaro-toolchain-binaries/trunk/2013.10/+download/gcc-linaro-arm-linux-gnueabihf-4.8-2013.10_win32.zip)
7670
77712.2 Script ejemplo para construir (adaptar los trayectos a como se necesiten)
7872
7973``` bat
8074set PATH=C:\pp\bin\i386-win32;%PATH%;
8175set FPCMAKEPATH=C:/pp
8276set FPCPATH=C:/pp
8377set OUTPATH=C:/pp271
8478%FPCMAKEPATH%/bin/i386-win32/make distclean OS_TARGET=linux CPU_TARGET=arm CROSSBINDIR=%FPCPATH%/bin/win32-armhf-linux CROSSOPT="-CpARMV6 -CfVFPV2 -OoFASTMATH" FPC=%FPCPATH%/bin/i386-win32/ppc386.exe
8579
8680%FPCMAKEPATH%/bin/i386-win32/make all OS_TARGET=linux CPU_TARGET=arm CROSSBINDIR=%FPCPATH%/bin/win32-armhf-linux CROSSOPT="-CpARMV6 -CfVFPV2 -OoFASTMATH" FPC=%FPCPATH%/bin/i386-win32/ppc386.exe
8781if errorlevel 1 goto quit
8882%FPCMAKEPATH%/bin/i386-win32/make crossinstall CROSSBINDIR=%FPCPATH%/bin/win32-armhf-linux CROSSOPT="-CpARMV6 -CfVFPV2 -OoFASTMATH" OS_TARGET=linux CPU_TARGET=arm FPC=%FPCPATH%/bin/i386-win32/ppc386.exe INSTALL_BASEDIR=%OUTPATH%
8983
9084:quit
9185pause
9286```
9387
9488Con el resultado de ppcrossarm.exe y ARM RTL deberias ser capaz de construir una versión de Lazarus para plataforma cruzada como habitualmente y compilar proyectos FPC para Raspberry Pi y otros dispositivos armhf. Recuerda que no todas las librerias, - especialmente en Windows - se encuentran disponibles para Linux arm.
9589
9690### Compilando desde el código fuente
9791
9892Puede que necesites compilar Lazarus a partir de sus fuentes subverion. Ver \[<http://www.michellcomputing.co.uk/blog/?p=72>: Michell Computing: Lazarus en la Raspberry Pi\] para más detalles..
9993
10094<File:Start> Menu with Lazarus en.png\|Como arrancar Lazarus en Raspbian Wheezy <File:Lazarus> on Raspberry Pi.jpg\|Lazarus bajo Raspberry Pi <File:rpi> gpio pins.png\|Numeración de los pines GPIO
10195
10296Compilando desde las fuentes en Raspberry con Gentoo (y otra distro)
10397
10498------------------------------------------------------------------------
10599
106100Si necesitas instalar la última release estable de fpc y, adicional y aisladamente, el compilador fpc del trunk entonces puedes leer la siguiente guía.
107101
108102Esto se escribió utilizando Gentoo, pero esta guía debería ser de utilidad para cualquier otra distro: [[Install fpc on Raspberry with Gentoo]]
109103
110104## Accediendo a hardware externo
111105
112-<figure>
113106<img src="rpi_pinout_all_50.png" title="Raspberry Pi pinout of external connectors" width="300" />
114-<figcaption>Raspberry Pi pinout of external connectors</figcaption>
115-</figure>
116107
117108Una de las finalidades en el desarrollo de Raspberry Pi fue la de facilitar el acceso sin esfuerzo a dispositivos externos tales como sensores y actuadores. A nivel de sofware desde FreePascal y Lazarus además presenta varias modalidades de acceso de E/S (Entrada/Salida) / (I/O (Input/Output):
118109
1191101. [[Lazarus on Raspberry Pi|Direct access]] Utilizando la unidad [[BaseUnix]].
1201112. Acceso a través de [[Lazarus on Raspberry Pi|encapsulated shell calls]]
1211123. Acceso a través de [[Lazarus on Raspberry Pi|wiringPi library]].
1221134. Acceso a través de la unidad [[Lazarus on Raspberry Pi|rpi_hal]].
1231145. Acceso a través de la unidad [[Lazarus on Raspberry Pi|PiGpio]].
1241156. Acceso a través de la librería [PascalIO](https://github.com/SAmeis/pascalio).
1251167. Acceso a través de la librería [PXL](http://asphyre.net/products/pxl).
126117
127118### Acceso nativo al hardware
128119
129120![ Programa simple de testeo que permite el acceso al puerto GPIO en Raspberry Pi\|thumb\|300px\|right](/wiki-images/d/d2/Testprogram_for_GPIO_on_RPI_annotated.png) ![Circuito de test para acceso GPIO con el programa asociado\|thumb\|300px\|right](/wiki-images/7/7c/Rpi_testcircuit_1d.png) ![Demo simple con la implementación del circuito propuesto en una placa de prototipos\|thumb\|300px\|right](/wiki-images/7/7e/Rpi_testcircuit_1p_annotaded.png) Este método provee acceso a hardware externo que no requiere librerías adicionales. El único requerimiento es la librería BaseUnix que es parte de la RTL de FreePascal.
130121
131122#### Conmutando un dispositivo a través de un puerto GPIO
132123
133124El siguiente ejemplo lista un programa simple que controla el pin 17 GPIO establecido como salida para conmutar el estado de un LED, transistor o relé. Este programa contiene un [[doc:lcl/stdctrls/ttogglebox.html|ToggleBox]] with name *GPIO17ToggleBox* y para logging retorna códigos a un [[doc:lcl/stdctrls/tmemo.html|TMemo]] llamado *LogMemo*.
134125
135126Para el ejemplo, el ánodo del LED se ha conectado al Pin 11 del conector Pi (que a su vez su correspondencia es con el pin 17 del chip BCM2835 SOC) y por otro lado el cátodo del LED se ha conectado al pin 6 del conector (que corresponde a masa (GND: Ground) pero poniendo una resistencia entre medias de 68 Ohm (R1 en el esquema) tal como se describió previamente por Upton and Halfacree (esto nos permite limitar convenientemente la intensidad que circula por el LED). Subsecuentemente el LED puede ser conmutado entre dos estados ON / OFF mediante el toggle box de la aplicación.
136127
137128El código puede requerir en un principio que se ejecute como root, i.e. adicionalmente con una cuenta tipo root (no recomendado) o a través del mandato **su** antepuesto al nombre del programa lo que nos promocionará el acceso como super usuario (su: super user). Una mejor opción es añadir el usuario con el que trabajemos a los grupos gpio, i2c y spi tal como se indica a continuación:
138129
139130``` bash
140131sudo adduser pi gpio
141132sudo adduser pi i2c
142133sudo adduser pi spi
143134```
144135
145136*Unidad de control:*
146137
147138``` pascal
148139unit Unit1;
149140
150141{Demo application for GPIO on Raspberry Pi}
151142{Inspired by the Python input/output demo application by Gareth Halfacree}
152143{written for the Raspberry Pi User Guide, ISBN 978-1-118-46446-5}
153144
154145{$mode objfpc}{$H+}
155146
156147interface
157148
158149uses
159150 Classes, SysUtils, FileUtil, Forms, Controls, Graphics, Dialogs, StdCtrls,
160151 Unix, BaseUnix;
161152
162153type
163154
164155 { TForm1 }
165156
166157 TForm1 = class(TForm)
167158 LogMemo: TMemo;
168159 GPIO17ToggleBox: TToggleBox;
169160 procedure FormActivate(Sender: TObject);
170161 procedure FormClose(Sender: TObject; var CloseAction: TCloseAction);
171162 procedure GPIO17ToggleBoxChange(Sender: TObject);
172163 private
173164 { private declarations }
174165 public
175166 { public declarations }
176167 end;
177168
178169const
179170 PIN_17: PChar = '17';
180171 PIN_ON: PChar = '1';
181172 PIN_OFF: PChar = '0';
182173 OUT_DIRECTION: PChar = 'out';
183174
184175var
185176 Form1: TForm1;
186177 gReturnCode: longint; {stores the result of the IO operation}
187178
188179implementation
189180
190181{$R *.lfm}
191182
192183{ TForm1 }
193184
194185procedure TForm1.FormActivate(Sender: TObject);
195186var
196187 fileDesc: integer;
197188begin
198189 { Prepare SoC pin 17 (pin 11 on GPIO port) for access: }
199190 try
200191 fileDesc := fpopen('/sys/class/gpio/export', O_WrOnly);
201192 gReturnCode := fpwrite(fileDesc, PIN_17[0], 2);
202193 LogMemo.Lines.Add(IntToStr(gReturnCode));
203194 finally
204195 gReturnCode := fpclose(fileDesc);
205196 LogMemo.Lines.Add(IntToStr(gReturnCode));
206197 end;
207198 { Set SoC pin 17 as output: }
208199 try
209200 fileDesc := fpopen('/sys/class/gpio/gpio17/direction', O_WrOnly);
210201 gReturnCode := fpwrite(fileDesc, OUT_DIRECTION[0], 3);
211202 LogMemo.Lines.Add(IntToStr(gReturnCode));
212203 finally
213204 gReturnCode := fpclose(fileDesc);
214205 LogMemo.Lines.Add(IntToStr(gReturnCode));
215206 end;
216207end;
217208
218209procedure TForm1.FormClose(Sender: TObject; var CloseAction: TCloseAction);
219210var
220211 fileDesc: integer;
221212begin
222213 { Free SoC pin 17: }
223214 try
224215 fileDesc := fpopen('/sys/class/gpio/unexport', O_WrOnly);
225216 gReturnCode := fpwrite(fileDesc, PIN_17[0], 2);
226217 LogMemo.Lines.Add(IntToStr(gReturnCode));
227218 finally
228219 gReturnCode := fpclose(fileDesc);
229220 LogMemo.Lines.Add(IntToStr(gReturnCode));
230221 end;
231222end;
232223
233224procedure TForm1.GPIO17ToggleBoxChange(Sender: TObject);
234225var
235226 fileDesc: integer;
236227begin
237228 if GPIO17ToggleBox.Checked then
238229 begin
239230 { Swith SoC pin 17 on: }
240231 try
241232 fileDesc := fpopen('/sys/class/gpio/gpio17/value', O_WrOnly);
242233 gReturnCode := fpwrite(fileDesc, PIN_ON[0], 1);
243234 LogMemo.Lines.Add(IntToStr(gReturnCode));
244235 finally
245236 gReturnCode := fpclose(fileDesc);
246237 LogMemo.Lines.Add(IntToStr(gReturnCode));
247238 end;
248239 end
249240 else
250241 begin
251242 { Switch SoC pin 17 off: }
252243 try
253244 fileDesc := fpopen('/sys/class/gpio/gpio17/value', O_WrOnly);
254245 gReturnCode := fpwrite(fileDesc, PIN_OFF[0], 1);
255246 LogMemo.Lines.Add(IntToStr(gReturnCode));
256247 finally
257248 gReturnCode := fpclose(fileDesc);
258249 LogMemo.Lines.Add(IntToStr(gReturnCode));
259250 end;
260251 end;
261252end;
262253
263254end.
264255```
265256
266257*Programa principal:*
267258
268259``` pascal
269260program io_test;
270261
271262{$mode objfpc}{$H+}
272263
273264uses
274265 {$IFDEF UNIX}{$IFDEF UseCThreads}
275266 cthreads,
276267 {$ENDIF}{$ENDIF}
277268 Interfaces, // this includes the LCL widgetset
278269 Forms, Unit1
279270 { puedes añadir unidades después de esto };
280271
281272{$R *.res}
282273
283274begin
284275 Application.Initialize;
285276 Application.CreateForm(TForm1, Form1);
286277 Application.Run;
287278end.
288279```
289280
290281#### Leyendo el estado de un pin
291282
292283![Programa de desmostración para la lectura del estado de un pin GPIO\|thumb\|300px\|right](/wiki-images/7/73/2013-04-28-193243_1280x1024_scrot.png) ![Circuito de chequeo para acceso GPIO mediante el programa mostrado\|thumb\|300px\|right](/wiki-images/f/f4/Rpi_testcircuit_2d.png) ![Posible implementación de este circuito de chequeo mediante el uso de placa de prototipos\|thumb\|300px\|right](/wiki-images/2/2f/Rpi_testcircuit_2p_annotaded.png)
293284
294285Por supuesto también es posible leer el estado de un pulsador conectado a un puerto GPIO (General Porpouse Inpunt Output).
295286
296287El siguiente ejemplo es muy similar al anterior. Controla el pin GPIO 18 como entrada para un dispositivo binario tal como un pulsador, un transistor o un relé. Este programa contiene un [[doc:lcl/stdctrls/tcheckbox.html|CheckBox]] con el nombre *GPIO18CheckBox* y un [[doc:lcl/stdctrls/tmemo.html|TMemo]] llamado *LogMemo* para los códigos retornados de logging.
297288
298289Para el ejemplo se ha conectado un pulsador al Pin 12 del conector de la Pi (correspondiente al pin GPIO 18 del SOC BCM2835) a través de una resistencia de 10 KOhm conectada al pin 1 (+3.3V, ver diagrama de cableado). El otro polo se ha cableado al pin 6 del conector (corresponde a la masa o GND). El programa detecta el estado del pulsador y commuta correlativamente a On u Off según el estado del mismo.
299290
300291Ten en cuenta que el potencial del pin 18 es "alto" (gracias a la conexión al pin 1 mediate la resistencia) si el pulsador está sin pulsar y "bajo" si se encuentra pulsado (porque en esta situación el pin 18 se encuentra conectado a masa (GND) a través del pulsador). Por tanto, el pin GPIO marca 0 si el botón está presionado y 1 si está sin pulsar.
301292
302293Este programa tiene que ser ejecutado también como usuario root.
303294
304295*Unidad de control:*
305296
306297``` pascal
307298unit Unit1;
308299
309300{Demo application for GPIO on Raspberry Pi}
310301{Inspired by the Python input/output demo application by Gareth Halfacree}
311302{written for the Raspberry Pi User Guide, ISBN 978-1-118-46446-5}
312303
313304{This application reads the status of a push-button}
314305
315306{$mode objfpc}{$H+}
316307
317308interface
318309
319310uses
320311 Classes, SysUtils, FileUtil, Forms, Controls, Graphics, Dialogs, StdCtrls,
321312 ButtonPanel, Unix, BaseUnix;
322313
323314type
324315
325316 { TForm1 }
326317
327318 TForm1 = class(TForm)
328319 ApplicationProperties1: TApplicationProperties;
329320 GPIO18CheckBox: TCheckBox;
330321 LogMemo: TMemo;
331322 procedure ApplicationProperties1Idle(Sender: TObject; var Done: Boolean);
332323 procedure FormActivate(Sender: TObject);
333324 procedure FormClose(Sender: TObject; var CloseAction: TCloseAction);
334325 private
335326 { private declarations }
336327 public
337328 { public declarations }
338329 end;
339330
340331const
341332 PIN_18: PChar = '18';
342333 IN_DIRECTION: PChar = 'in';
343334
344335var
345336 Form1: TForm1;
346337 gReturnCode: longint; {stores the result of the IO operation}
347338
348339implementation
349340
350341{$R *.lfm}
351342
352343{ TForm1 }
353344
354345procedure TForm1.FormActivate(Sender: TObject);
355346var
356347 fileDesc: integer;
357348begin
358349 { Prepare SoC pin 18 (pin 12 on GPIO port) for access: }
359350 try
360351 fileDesc := fpopen('/sys/class/gpio/export', O_WrOnly);
361352 gReturnCode := fpwrite(fileDesc, PIN_18[0], 2);
362353 LogMemo.Lines.Add(IntToStr(gReturnCode));
363354 finally
364355 gReturnCode := fpclose(fileDesc);
365356 LogMemo.Lines.Add(IntToStr(gReturnCode));
366357 end;
367358 { Set SoC pin 18 as input: }
368359 try
369360 fileDesc := fpopen('/sys/class/gpio/gpio18/direction', O_WrOnly);
370361 gReturnCode := fpwrite(fileDesc, IN_DIRECTION[0], 2);
371362 LogMemo.Lines.Add(IntToStr(gReturnCode));
372363 finally
373364 gReturnCode := fpclose(fileDesc);
374365 LogMemo.Lines.Add(IntToStr(gReturnCode));
375366 end;
376367end;
377368
378369procedure TForm1.ApplicationProperties1Idle(Sender: TObject; var Done: Boolean);
379370var
380371 fileDesc: integer;
381372 buttonStatus: string[1] = '1';
382373begin
383374 try
384375 { Open SoC pin 18 (pin 12 on GPIO port) in read-only mode: }
385376 fileDesc := fpopen('/sys/class/gpio/gpio18/value', O_RdOnly);
386377 if fileDesc > 0 then
387378 begin
388379 { Read status of this pin (0: button pressed, 1: button released): }
389380 gReturnCode := fpread(fileDesc, buttonStatus[1], 1);
390381 LogMemo.Lines.Add(IntToStr(gReturnCode) + ': ' + buttonStatus);
391382 LogMemo.SelStart := Length(LogMemo.Lines.Text) - 1;
392383 if buttonStatus = '0' then
393384 GPIO18CheckBox.Checked := true
394385 else
395386 GPIO18CheckBox.Checked := false;
396387 end;
397388 finally
398389 { Close SoC pin 18 (pin 12 on GPIO port) }
399390 gReturnCode := fpclose(fileDesc);
400391 LogMemo.Lines.Add(IntToStr(gReturnCode));
401392 LogMemo.SelStart := Length(LogMemo.Lines.Text) - 1;
402393 end;
403394end;
404395
405396procedure TForm1.FormClose(Sender: TObject; var CloseAction: TCloseAction);
406397var
407398 fileDesc: integer;
408399begin
409400 { Free SoC pin 18: }
410401 try
411402 fileDesc := fpopen('/sys/class/gpio/unexport', O_WrOnly);
412403 gReturnCode := fpwrite(fileDesc, PIN_18[0], 2);
413404 LogMemo.Lines.Add(IntToStr(gReturnCode));
414405 finally
415406 gReturnCode := fpclose(fileDesc);
416407 LogMemo.Lines.Add(IntToStr(gReturnCode));
417408 end;
418409end;
419410
420411end.
421412```
422413
423414El programa main es idéntico al del ejemplo de arriba.
424415
425416### Acceso hardware mediante llamadas encapsuladas del shell
426417
427418Otro modo de acceder al hardware es mediante el encapsulamiento de mandatos a través del shell. Esto se consigue mediante el uso de la función [[Executing External Programs|fpsystem]]. Este método permite el acceso a funciones que no están soportadas por la unidad BaseUnix. El siguiente código implementa un programa que tiene la misma funcionalidad que as the program resulting from the first listing above.
428419
429420*Controlling unit:*
430421
431422``` pascal
432423unit Unit1;
433424
434425{Demo application for GPIO on Raspberry Pi}
435426{Inspired by the Python input/output demo application by Gareth Halfacree}
436427{written for the Raspberry Pi User Guide, ISBN 978-1-118-46446-5}
437428
438429{$mode objfpc}{$H+}
439430
440431interface
441432
442433uses
443434 Classes, SysUtils, FileUtil, Forms, Controls, Graphics, Dialogs, StdCtrls, Unix;
444435
445436type
446437
447438 { TForm1 }
448439
449440 TForm1 = class(TForm)
450441 LogMemo: TMemo;
451442 GPIO17ToggleBox: TToggleBox;
452443 procedure FormActivate(Sender: TObject);
453444 procedure FormClose(Sender: TObject; var CloseAction: TCloseAction);
454445 procedure GPIO17ToggleBoxChange(Sender: TObject);
455446 private
456447 { private declarations }
457448 public
458449 { public declarations }
459450 end;
460451
461452var
462453 Form1: TForm1;
463454 gReturnCode: longint; {stores the result of the IO operation}
464455
465456implementation
466457
467458{$R *.lfm}
468459
469460{ TForm1 }
470461
471462procedure TForm1.FormActivate(Sender: TObject);
472463begin
473464 { Prepare SoC pin 17 (pin 11 on GPIO port) for access: }
474465 gReturnCode := fpsystem('echo "17" > /sys/class/gpio/export');
475466 LogMemo.Lines.Add(IntToStr(gReturnCode));
476467 { Set SoC pin 17 as output: }
477468 gReturnCode := fpsystem('echo "out" > /sys/class/gpio/gpio17/direction');
478469 LogMemo.Lines.Add(IntToStr(gReturnCode));
479470end;
480471
481472procedure TForm1.FormClose(Sender: TObject; var CloseAction: TCloseAction);
482473begin
483474 { Free SoC pin 17: }
484475 gReturnCode := fpsystem('echo "17" > /sys/class/gpio/unexport');
485476 LogMemo.Lines.Add(IntToStr(gReturnCode));
486477end;
487478
488479procedure TForm1.GPIO17ToggleBoxChange(Sender: TObject);
489480begin
490481 if GPIO17ToggleBox.Checked then
491482 begin
492483 { Swith SoC pin 17 on: }
493484 gReturnCode := fpsystem('echo "1" > /sys/class/gpio/gpio17/value');
494485 LogMemo.Lines.Add(IntToStr(gReturnCode));
495486 end
496487 else
497488 begin
498489 { Switch SoC pin 17 off: }
499490 gReturnCode := fpsystem('echo "0" > /sys/class/gpio/gpio17/value');
500491 LogMemo.Lines.Add(IntToStr(gReturnCode));
501492 end;
502493end;
503494
504495end.
505496```
506497
507498El programa main es idéntico al del ejemplo de arriba. Este programa necesita ejecutarse con privilegios de root también.
508499
509500### Procedimientos y funciones de wiringPi
510501
511502Alex Schaller's wrapper unit for Gordon Henderson's Arduino compatible wiringPi library provides a numbering scheme that resembles that of Arduino boards.
512503
513504**Function wiringPiSetup:longint:** Initializes wiringPi system using the wiringPi pin numbering scheme.
514505
515506**Procedure wiringPiGpioMode(mode:longint):** Initializes wiringPi system with the Broadcom GPIO pin numbering scheme.
516507
517508**Procedure pullUpDnControl(pin:longint;** pud:longint): controls the internal pull-up/down resistors on a GPIO pin.
518509
519510**Procedure pinMode(pin:longint; mode:longint):** sets the mode of a pin to either INPUT, OUTPUT, or PWM_OUTPUT.
520511
521512**Procedure digitalWrite(pin:longint; value:longint):** sets an output bit.
522513
523514**Procedure pwmWrite(pin:longint; value:longint):** sets an output PWM value between 0 and 1024.
524515
525516**Function digitalRead(pin:longint):longint:** reads the value of a given Pin, returning 1 or 0.
526517
527518**Procedure delay(howLong:dword):** waits for at least howLong milliseconds.
528519
529520**Procedure delayMicroseconds(howLong:dword):** waits for at least howLong microseconds.
530521
531522**Function millis:dword:** returns the number of milliseconds since the program called one of the wiringPiSetup functions.
532523
533524### rpi_hal-Hardware Abstraction Library (funciones y procedimientos GPIO, I2C y SPI de la librería de abstracción hardware de la RaspBerry Pi)
534525
535526Esta unidad con cerca de 1700 líneas de código aportada por Stefan Fischer, aporta procedimientos y funciones para acceso HW I2C, SPI y GPIO en la RaspBerry Pi:
536527
537528Justamente un extracto de los procedimientos y funciones disponibles:
538529
539530**procedure gpio_set_pin (pin:longword;highlevel:boolean);** { Establece RPi GPIO pin a nivel alto o bajo; Velocidad @ 700MHz -\> 0.65MHz }
540531
541532**function gpio_get_PIN (pin:longword):boolean;** { Get RPi GPIO pin Level is true when Pin level is '1'; false when '0'; Speed @ 700MHz -\> 1.17MHz }
542533
543534**procedure gpio_set_input (pin:longword);** { Establece RPi GPIO pin en modo entrada }
544535
545536**procedure gpio_set_output(pin:longword);** { Establece RPi GPIO pin en modo salida}
546537
547538**procedure gpio_set_alt (pin,altfunc:longword);** { Establece RPi GPIO pin to alternate function nr. 0..5 }
548539
549540**procedure gpio_set_gppud (mask:longword);** { Establece RPi GPIO Pull-up/down Register (GPPUD) with mask }
550541
551542...
552543
553544**function rpi_snr :string;** { Emtrega el SNR: 0000000012345678 }
554545
555546**function rpi_hw :string;** { Entrega el tipo de procesador: BCM2708 }
556547
557548**function rpi_proc:string;** { ARMv6-compatible processor rev 7 (v6l) }
558549
559550...
560551
561552**function i2c_bus_write(baseadr,reg:word; var <data:databuf_t>; lgt:byte; testnr:integer) : integer;**
562553
563554**function i2c_bus_read (baseadr,reg:word; var <data:databuf_t>; lgt:byte; testnr:integer) : integer;**
564555
565556**function i2c_string_read(baseadr,reg:word; var <data:databuf_t>; lgt:byte; testnr:integer) : string;**
566557
567558**function i2c_string_write(baseadr,reg:word; s:string; testnr:integer) : integer;**
568559
569560...
570561
571562**procedure SPI_Write(devnum:byte; reg,data:word);**
572563
573564**function SPI_Read(devnum:byte; reg:word) : byte;**
574565
575566**procedure SPI_BurstRead2Buffer (devnum,start_reg:byte; xferlen:longword);**
576567
577568**procedure SPI_BurstWriteBuffer (devnum,start_reg:byte; xferlen:longword);** { Write 'len' Bytes from Buffer SPI Dev startig at address 'reg' }
578569
579570...
580571
581572*Test Program (testrpi.pas):*
582573
583574``` pascal
584575//Progama simple de chequeo, el cual utiliza rpi_hal;
585576
586577 program testrpi;
587578 uses rpi_hal;
588579 begin
589580 writeln('Show CPU-Info, RPI-HW-Info and Registers:');
590581 rpi_show_all_info;
591582 writeln('Let Status LED Blink. Using GPIO functions:');
592583 GPIO_PIN_TOGGLE_TEST;
593584 writeln('Test SPI Read function. (piggy back board with installed RFM22B Module is required!)');
594585 Test_SPI;
595586 end.
596587```
597588
598589### Unidad nativa PiGpio de bajo nivel escrita en pascal (control GPIO en lugar de la librería c de wiringPi)
599590
600591*Esta unit (pigpio.pas[2](https://docs.google.com/file/d/0B-b-5ooIWPvGN1BIcEJzRDgyeUE/edit?usp=sharing)) de 270 líneas de código aportada por Gabor Szollosi, funciona muy rápido (para ex. GPIO pin output conmutando a una frecuencia de 8 MHz) :*
601592
602593``` pascal
603594
604595unit PiGpio;
605596{
606597 BCM2835 GPIO Registry Driver, also can use to manipulate cpu other registry areas
607598
608599 This code is tested only Broadcom bcm2835 cpu, different arm cpus may need different
609600 gpio driver implementation
610601
611602 2013 Gabor Szollosi
612603}
613604{$mode objfpc}{$H+}
614605
615606interface
616607
617608uses
618609 Classes, SysUtils;
619610
620611const
621612 REG_GPIO = $3F000;// bcm2835 gpio register 0x2000 0000 (RPi1), 0x3F00 0000 (RPi2)
622613 // new fpMap uses page offset, one page is 4096 bytes = 0x1000 so simply calculate 0x2000 0000 / 0x1000 = 0x2000 0
623614 PAGE_SIZE = 4096;
624615 BLOCK_SIZE = 4096;
625616 // The BCM2835 has 54 GPIO pins.
626617 // BCM2835 data sheet, Page 90 onwards.
627618 // There are 6 control registers, each control the functions of a block
628619 // of 10 pins.
629620
630621 CLOCK_BASE = (REG_GPIO + $101);
631622 GPIO_BASE = (REG_GPIO + $200);
632623 GPIO_PWM = (REG_GPIO + $20C);
633624
634625 INPUT = 0;
635626 OUTPUT = 1;
636627 PWM_OUTPUT = 2;
637628 LOW = False;
638629 HIGH = True;
639630 PUD_OFF = 0;
640631 PUD_DOWN = 1;
641632 PUD_UP = 2;
642633
643634 // PWM
644635
645636 PWM_CONTROL = 0;
646637 PWM_STATUS = 4;
647638 PWM0_RANGE = 16;
648639 PWM0_DATA = 20;
649640 PWM1_RANGE = 32;
650641 PWM1_DATA = 36;
651642
652643 PWMCLK_CNTL = 160;
653644 PWMCLK_DIV = 164;
654645
655646 PWM1_MS_MODE = $8000; // Run in MS mode
656647 PWM1_USEFIFO = $2000; // Data from FIFO
657648 PWM1_REVPOLAR = $1000; // Reverse polarity
658649 PWM1_OFFSTATE = $0800; // Ouput Off state
659650 PWM1_REPEATFF = $0400; // Repeat last value if FIFO empty
660651 PWM1_SERIAL = $0200; // Run in serial mode
661652 PWM1_ENABLE = $0100; // Channel Enable
662653
663654 PWM0_MS_MODE = $0080; // Run in MS mode
664655 PWM0_USEFIFO = $0020; // Data from FIFO
665656 PWM0_REVPOLAR = $0010; // Reverse polarity
666657 PWM0_OFFSTATE = $0008; // Ouput Off state
667658 PWM0_REPEATFF = $0004; // Repeat last value if FIFO empty
668659 PWM0_SERIAL = $0002; // Run in serial mode
669660 PWM0_ENABLE = $0001; // Channel Enable
670661
671662type
672663
673664 { TIoPort }
674665
675666 TIoPort = class // IO bank object
676667 private //
677668
678669 //function get_pinDirection(aPin: TGpIoPin): TGpioPinConf;
679670
680671 public
681672 FGpio: ^LongWord;
682673 FClk: ^LongWord;
683674 FPwm: ^LongWord;
684675 procedure SetPinMode(gpin, mode: byte);
685676 function GetBit(gpin : byte):boolean;inline; // gets pin bit}
686677 procedure ClearBit(gpin : byte);inline;// write pin to 0
687678 procedure SetBit(gpin : byte);inline;// write pin to 1
688679 procedure SetPullMode(gpin, mode: byte);
689680 procedure PwmWrite(gpin : byte; value : LongWord);inline;// write pin to pwm value
690681 end;
691682
692683 { TIoDriver }
693684
694685 TIoDriver = class
695686 private
696687
697688 public
698689 destructor Destroy;override;
699690 function MapIo:boolean;// creates io memory mapping
700691 procedure UnmapIoRegisrty(FMap: TIoPort);// close io memory mapping
701692 function CreatePort(PortGpio, PortClk, PortPwm: LongWord):TIoPort; // create new IO port
702693 end;
703694
704695var
705696
706697 fd: integer;// /dev/mem file handle
707698procedure delayNanoseconds (howLong : LongWord);
708699
709700implementation
710701
711702uses
712703 baseUnix, Unix;
713704
714705procedure delayNanoseconds (howLong : LongWord);
715706var
716707 sleeper, dummy : timespec;
717708begin
718709 sleeper.tv_sec := 0 ;
719710 sleeper.tv_nsec := howLong ;
720711 fpnanosleep (@sleeper,@dummy) ;
721712end;
722713{ TIoDriver }
723714//*******************************************************************************
724715destructor TIoDriver.Destroy;
725716begin
726717 inherited Destroy;
727718end;
728719//*******************************************************************************
729720function TIoDriver.MapIo: boolean;
730721begin
731722 Result := True;
732723 fd := fpopen('/dev/mem', O_RdWr or O_Sync); // Open the master /dev/memory device
733724 if fd < 0 then
734725 begin
735726 Result := False; // unsuccessful memory mapping
736727 end;
737728 //
738729end;
739730//*******************************************************************************
740731procedure TIoDriver.UnmapIoRegisrty(FMap:TIoPort);
741732begin
742733 if FMap.FGpio <> nil then
743734 begin
744735 fpMUnmap(FMap.FGpio,PAGE_SIZE);
745736 FMap.FGpio := Nil;
746737 end;
747738 if FMap.FClk <> nil then
748739 begin
749740 fpMUnmap(FMap.FClk,PAGE_SIZE);
750741 FMap.FClk := Nil;
751742 end;
752743 if FMap.FPwm <> nil then
753744 begin
754745 fpMUnmap(FMap.FPwm ,PAGE_SIZE);
755746 FMap.FPwm := Nil;
756747 end;
757748end;
758749//*******************************************************************************
759750function TIoDriver.CreatePort(PortGpio, PortClk, PortPwm: LongWord): TIoPort;
760751begin
761752 Result := TIoPort.Create;// new io port, pascal calls new fpMap, where offst is page sized 4096 bytes!!!
762753 Result.FGpio := FpMmap(Nil, PAGE_SIZE, PROT_READ or PROT_WRITE, MAP_SHARED, fd, PortGpio); // port config gpio memory
763754 Result.FClk:= FpMmap(Nil, PAGE_SIZE, PROT_READ or PROT_WRITE, MAP_SHARED, fd, PortClk);; // port clk
764755 Result.FPwm:= FpMmap(Nil, PAGE_SIZE, PROT_READ or PROT_WRITE, MAP_SHARED, fd, PortPwm);; // port pwm
765756end;
766757//*******************************************************************************
767758procedure TIoPort.SetPinMode(gpin, mode: byte);
768759var
769760 fSel, shift, alt : byte;
770761 gpiof, clkf, pwmf : ^LongWord;
771762begin
772763 fSel := (gpin div 10)*4 ; //Select Gpfsel 0 to 5 register
773764 shift := (gpin mod 10)*3 ; //0-9 pin shift
774765 gpiof := Pointer(LongWord(Self.FGpio)+fSel);
775766 if (mode = INPUT) then
776767 gpiof^ := gpiof^ and ($FFFFFFFF - (7 shl shift)) //7 shl shift komplemens - Sets bits to zero = input
777768 else if (mode = OUTPUT) then
778769 begin
779770 gpiof^ := gpiof^ and ($FFFFFFFF - (7 shl shift)) or (1 shl shift);
780771 end
781772 else if (mode = PWM_OUTPUT) then
782773 begin
783774 Case gpin of
784775 12,13,40,41,45 : alt:= 4 ;
785776 18,19 : alt:= 2 ;
786777 else alt:= 0 ;
787778 end;
788779 If alt > 0 then
789780 begin
790781 gpiof^ := gpiof^ and ($FFFFFFFF - (7 shl shift)) or (alt shl shift);
791782 clkf := Pointer(LongWord(Self.FClk)+PWMCLK_CNTL);
792783 clkf^ := $5A000011 or (1 shl 5) ; //stop clock
793784 delayNanoseconds(200);
794785 clkf := Pointer(LongWord(Self.FClk)+PWMCLK_DIV);
795786 clkf^ := $5A000000 or (32 shl 12) ; // set pwm clock div to 32 (19.2/3 = 600KHz)
796787 clkf := Pointer(LongWord(Self.FClk)+PWMCLK_CNTL);
797788 clkf^ := $5A000011 ; //start clock
798789 Self.ClearBit(gpin);
799790 pwmf := Pointer(LongWord(Self.FPwm)+PWM_CONTROL);
800791 pwmf^ := 0 ; // Disable PWM
801792 delayNanoseconds(200);
802793 pwmf := Pointer(LongWord(Self.FPwm)+PWM0_RANGE);
803794 pwmf^ := $400 ; //max: 1023
804795 delayNanoseconds(200);
805796 pwmf := Pointer(LongWord(Self.FPwm)+PWM1_RANGE);
806797 pwmf^ := $400 ; //max: 1023
807798 delayNanoseconds(200);
808799 // Enable PWMs
809800 pwmf := Pointer(LongWord(Self.FPwm)+PWM0_DATA);
810801 pwmf^ := 0 ; //start value
811802 pwmf := Pointer(LongWord(Self.FPwm)+PWM1_DATA);
812803 pwmf^ := 0 ; //start value
813804 pwmf := Pointer(LongWord(Self.FPwm)+PWM_CONTROL);
814805 pwmf^ := PWM0_ENABLE or PWM1_ENABLE ;
815806 end;
816807 end;
817808end;
818809//*******************************************************************************
819810procedure TIoPort.SetBit(gpin : byte);
820811var
821812 gpiof : ^LongWord;
822813begin
823814 gpiof := Pointer(LongWord(Self.FGpio) + 28 + (gpin shr 5) shl 2);
824815 gpiof^ := 1 shl gpin;
825816end;
826817//*******************************************************************************
827818procedure TIoPort.ClearBit(gpin : byte);
828819var
829820 gpiof : ^LongWord;
830821begin
831822 gpiof := Pointer(LongWord(Self.FGpio) + 40 + (gpin shr 5) shl 2);
832823 gpiof^ := 1 shl gpin;
833824end;
834825//*******************************************************************************
835826function TIoPort.GetBit(gpin : byte):boolean;
836827var
837828 gpiof : ^LongWord;
838829begin
839830 gpiof := Pointer(LongWord(Self.FGpio) + 52 + (gpin shr 5) shl 2);
840831 if (gpiof^ and (1 shl gpin)) = 0 then Result := False else Result := True;
841832end;
842833//*******************************************************************************
843834procedure TIoPort.SetPullMode(gpin, mode: byte);
844835var
845836 pudf, pudclkf : ^LongWord;
846837begin
847838 pudf := Pointer(LongWord(Self.FGpio) + 148 );
848839 pudf^ := mode; //mode = 0, 1, 2 :Off, Down, Up
849840 delayNanoseconds(200);
850841 pudclkf := Pointer(LongWord(Self.FGpio) + 152 + (gpin shr 5) shl 2);
851842 pudclkf^ := 1 shl gpin ;
852843 delayNanoseconds(200);
853844 pudf^ := 0 ;
854845 pudclkf^ := 0 ;
855846end;
856847//*******************************************************************************
857848procedure TIoPort.PwmWrite(gpin : byte; value : Longword);
858849var
859850 pwmf : ^LongWord;
860851 port : byte;
861852begin
862853 Case gpin of
863854 12,18,40 : port:= PWM0_DATA ;
864855 13,19,41,45 : port:= PWM1_DATA ;
865856 else exit;
866857 end;
867858 pwmf := Pointer(LongWord(Self.FPwm) + port);
868859 pwmf^ := value and $FFFFFBFF; // $400 complemens
869860end;
870861//*******************************************************************************
871862end.
872863```
873864
874865*Controlling Lazarus unit:(Project files[3](https://drive.google.com/folderview?id=0B-b-5ooIWPvGU043ZTZ0cUc2YkE&usp=sharing))*
875866
876867``` pascal
877868unit Unit1;
878869
879870{Demo application for GPIO on Raspberry Pi}
880871{Inspired by the Python input/output demo application by Gareth Halfacree}
881872{written for the Raspberry Pi User Guide, ISBN 978-1-118-46446-5}
882873
883874{$mode objfpc}{$H+}
884875
885876interface
886877
887878uses
888879 Classes, SysUtils, FileUtil, Forms, Controls, Graphics, Dialogs, StdCtrls,
889880 ExtCtrls, Unix, PiGpio;
890881
891882type
892883
893884 { TForm1 }
894885
895886 TForm1 = class(TForm)
896887 GPIO25In: TButton;
897888 SpeedButton: TButton;
898889 LogMemo: TMemo;
899890 GPIO23switch: TToggleBox;
900891 Timer1: TTimer;
901892 GPIO18Pwm: TToggleBox;
902893 Direction: TToggleBox;
903894 procedure DirectionChange(Sender: TObject);
904895 procedure GPIO18PwmChange(Sender: TObject);
905896 procedure GPIO25InClick(Sender: TObject);
906897 procedure FormActivate(Sender: TObject);
907898 procedure FormClose(Sender: TObject; var CloseAction: TCloseAction);
908899 procedure GPIO23switchChange(Sender: TObject);
909900 procedure SpeedButtonClick(Sender: TObject);
910901 procedure Timer1Timer(Sender: TObject);
911902 private
912903 { private declarations }
913904 public
914905 { public declarations }
915906 end;
916907
917908const
918909 INPUT = 0;
919910 OUTPUT = 1;
920911 PWM_OUTPUT = 2;
921912 LOW = False;
922913 HIGH = True;
923914 PUD_OFF = 0;
924915 PUD_DOWN = 1;
925916 PUD_UP = 2;
926917 // Convert Raspberry Pi P1 pins (Px) to GPIO port
927918 P3 = 0;
928919 P5 = 1;
929920 P7 = 4;
930921 P8 = 14;
931922 P10 = 15;
932923 P11 = 17;
933924 P12 = 18;
934925 P13 = 21;
935926 P15 = 22;
936927 P16 = 23;
937928 P18 = 24;
938929 P19 = 10;
939930 P21 = 9;
940931 P22 = 25;
941932 P23 = 11;
942933 P24 = 8;
943934 P26 = 7;
944935
945936var
946937 Form1: TForm1;
947938 GPIO_Driver: TIoDriver;
948939 GpF: TIoPort;
949940 PWM :Boolean;
950941 i, d : integer;
951942 Pin,Pout,Ppwm : byte;
952943
953944implementation
954945
955946{$R *.lfm}
956947
957948{ TForm1 }
958949
959950procedure TForm1.FormActivate(Sender: TObject);
960951begin
961952 if not GPIO_Driver.MapIo then
962953 begin
963954 LogMemo.Lines.Add('Error mapping gpio registry');
964955 end
965956 else
966957 begin
967958 GpF := GpIo_Driver.CreatePort(GPIO_BASE, CLOCK_BASE, GPIO_PWM);
968959 end ;
969960 Timer1.Enabled:= True;
970961 Timer1.Interval:= 25; //25 ms controll interval
971962 Pin := P22;
972963 Pout := P16;
973964 Ppwm := P12;
974965 i:=1;
975966 GpF.SetPinMode(Pout,OUTPUT);
976967 GpF.SetPinMode(Pin,INPUT);
977968 GpF.SetPullMode(Pin,PUD_Up); // Input PullUp High level
978969end;
979970
980971procedure TForm1.GPIO25InClick(Sender: TObject);
981972begin
982973 If GpF.GetBit(Pin) then LogMemo.Lines.Add('In: '+IntToStr(1))
983974 else LogMemo.Lines.Add('In: '+IntToStr(0));
984975end;
985976
986977procedure TForm1.GPIO18PwmChange(Sender: TObject);
987978begin
988979 if GPIO18Pwm.Checked then
989980 begin
990981 GpF.SetPinMode(Ppwm,PWM_OUTPUT);
991982 PWM := True; //PWM on
992983 end
993984 else
994985 begin
995986 GpF.SetPinMode(Ppwm,INPUT);
996987 PWM := False; //PWM off
997988 end;
998989end;
999990
1000991procedure TForm1.DirectionChange(Sender: TObject);
1001992begin
1002993 if Direction.Checked then d:=10 else d:=-10;
1003994end;
1004995
1005996
1006997procedure TForm1.FormClose(Sender: TObject; var CloseAction: TCloseAction);
1007998begin
1008999 GpF.SetPinMode(Ppwm,INPUT);
10091000 GpF.ClearBit(Pout);
10101001 GpIo_Driver.UnmapIoRegisrty(GpF);
10111002end;
10121003
10131004procedure TForm1.GPIO23switchChange(Sender: TObject);
10141005
10151006Begin
10161007 Timer1.Enabled := False;
10171008 if GPIO23switch.Checked then
10181009 begin
10191010 GpF.SetBit(Pout); //Turn LED on
10201011 end
10211012 else
10221013 begin
10231014 GpF.ClearBit(Pout); //Turn LED off
10241015 end;
10251016 Timer1.Enabled := True;
10261017end;
10271018
10281019procedure TForm1.SpeedButtonClick(Sender: TObject);
10291020var
10301021 i,p,k,v: longint;
10311022 ido:TDateTime;
10321023begin
10331024 ido:= Time;
10341025 k:= TimeStampToMSecs(DateTimeToTimeStamp(ido));
10351026 LogMemo.Lines.Add('Start: '+TimeToStr(ido));
10361027 p:=10000000 ;
10371028 For i:=1 to p do Begin
10381029 GpF.SetBit(P16);
10391030 GpF.ClearBit(P16);
10401031 end;
10411032 ido:= Time;
10421033 v:= TimeStampToMSecs(DateTimeToTimeStamp(ido));
10431034 LogMemo.Lines.Add('Stop: '+TimeToStr(ido)+' Frequency: '+
10441035 IntToStr(p div (v-k))+' kHz');
10451036end;
10461037
10471038procedure TForm1.Timer1Timer(Sender: TObject);
10481039begin
10491040 If PWM then Begin
10501041 If (d > 0) and (i+d < 1024) then begin
10511042 i:=i+d;
10521043 GpF.PwmWrite(Ppwm,i);
10531044 end ;
10541045 If (d < 0) and (i+d > -1) then begin
10551046 i:=i+d;
10561047 GpF.PwmWrite(Ppwm,i);
10571048 end;
10581049 end;
10591050end;
10601051
10611052
10621053end.
10631054```
10641055
10651056### PXL (Platform eXtended Library) for low level native access to GPIO, I²C, SPI, PWM, UART, V4L2, displays and sensors
10661057
10671058- Fácil y rápido acceso a GPIO, I²C, SPI, PWM, UART y timer de alta preción de la CPU.
10681059- V4L2 captura de video/imagen utilizando los conectores dedicados de la placa y cámaras USB. Por ejemplo cámaras serie como VC0706 y LSY201.
10691060- OpenGL ES hardware de renderizado con y sin servidor X. Software de renderizado.
10701061- Pantallas I²C y SPI tales como SSD1306, SSD1351, PCB8544 (Nokia), HX8357 y ILI9340.
10711062- LCD de caracteres con cableado de pines directo.
10721063- Suporte para software SPI y UART (bit-banging).
10731064- Suporte para SC16IS7x0 (controladora UART conectada a través de I²C o SPI), incluyendo pins GPIO extra.
10741065- Soporte para sensores tales como BMP180, DHT22, L3GD20, LSM303 y SHT10.
10751066- Otras características como networking, math, transformación de imágenes, efectos, dibujo de primitivas gráficas...
10761067
10771068*Más información y descargas de la [librería PXL](http://asphyre.net/products/pxl).*
10781069
10791070## Referencias
10801071
10811072- Eben Upton and Gareth Halfacree. Raspberry Pi User Guide. John Wiley and Sons, Chichester 2012, ISBN 111846446X
10821073- B. J. Rao (2013) The Raspberry Pi, Pi Vision and Lazarus/FPC. [Blaise Pascal Magazine](http://www.blaisepascal.eu). 29: 14-21.
10831074
10841075## External Links
10851076
10861077- [Raspberry Pi Foundation](http://www.raspberrypi.org)
10871078- [Raspberry Pi Spy: Raspberry Pi tutorials, scripts, help and downloads](http://www.raspberrypi-spy.co.uk)
10881079- [Lazarus wrapper unit for Gordon Henderson's wiringPi C library](http://www.lazarus.freepascal.org/index.php/topic,17404.0.html)
10891080- [Pin layout of the wiringPi library](https://projects.drogon.net/raspberry-pi/wiringpi/pins/)
10901081- [Additional information on Lazarus and Raspberry Pi at eLinux.org](http://www.elinux.org/Lazarus_on_RPi)
10911082- [Getting Started with Pascal on the Pi](http://www.pp4s.co.uk/main/gs-pi-intro.html)
10921083- [Lazberry Pi: Comprehensive information on Lazarus on the Raspberry Pi computer](http://superbitysoft.co.uk/lazberrypi/).
10931084- [Stefan Fischer's Lazarus unit rpi_hal](http://www.lazarus.freepascal.org/index.php/topic,20991.0.html).
10941085- [Improved Lazarus Unit for fast access to GPIO](http://www.meltonisl.com/software.html).
10951086- [PXL - Platform eXtended Library](http://asphyre.net/products/pxl).
10961087
10971088---
10981089*From the Free Pascal wiki, page "Lazarus on Raspberry Pi/es", as it stood on 2020-02-19 after a change by Trev, out of the wiki's dump of 2024-05-26. Copyright stays with the author who wrote it, according to the old wiki's [[Licensing]] page. If you have concerns about this material, [message the admin](/wiki-contact).*

Back to history