bifferboard

Recent site activity

Home‎ > ‎HowTo‎ > ‎

Qemu

S3282 (and other RDC CPUs) can be emulated with a patch to Qemu. 

What gets emulated
  • 486 CPU, with 32MB RAM
  • Serial port
  • PCI vendor ID and Customer IDs on the northbridge.  See the patch and it should be obvious how to change these values to emulate other RDC CPUs.
  • OHCI controller
  • Missing cpuid instruction

What doesn't get emulated (TODO)
  • r6040 Ethernet controller (this will be difficult).
  • Missing FPU - Linux still probes (and finds) an FPU, it would be good to disable this in Qemu, but I can't work out how
  • GPIO (should be fairly easy).

Here's how to do this
  • wget http://download.savannah.gnu.org/releases/qemu/qemu-0.10.5.tar.gz
  • tar xvf qemu-0.10.5.tar.gz
  • cd qemu-0.10.5
  • patch -p1 < ../qemu-rdc-0.10.5.patch        # Emulate RDC SoC (kind-of).
  • ./configure --target-list=i386-softmmu    # Not all targets usually build OK, so it's good to just build 386.
  • make                                                     # to build qemu
  • make install                                      # run as root
  • Ensure you have bzImage and biffboot.bin in this directory
  • python add_kernel_to_loader.py bzImage biffboot.bin     # to produce 'bios.bin'
  • cp /usr/local/share/qemu/vgabios-cirrus.bin .
  • qemu -cpu rdc -m 32 -nographic -usb -no-acpi -L ./ -serial stdio -hda /dev/zero
  • CTRL-A X quits the emulator
Assuming you have a flash disk with a Bifferboard rootfs on it, insert it but don't mount it.  After a few seconds run lsusb, you should see something like this:

$ lsusb
Bus 001 Device 018: ID 0951:1605 Kingston Technology
Bus 001 Device 001: ID 1d6b:0002 Linux Foundation 2.0 root hub
Bus 004 Device 001: ID 1d6b:0001 Linux Foundation 1.1 root hub
Bus 002 Device 001: ID 1d6b:0001 Linux Foundation 1.1 root hub
Bus 003 Device 001: ID 1d6b:0001 Linux Foundation 1.1 root hub

Make a note of the Bus and Device number of your flash disk (001 and 018 in the above example), and add them to the Qemu command line, e.g.:

-usbdevice host:1.18

Qemu should now boot from the flash disk.  It is also possible to attach a USB mass storage device in a container file with an option like "-usbdevice disk:usb_root.img", see the Qemu documentation for details.


Introducing the GPIO panel

The Panel (or more specifically Patch Panel) can be considered a collection of GPIO pins.  The panel is represented by a socket server which tracks the states of the pins owned by the panel.  Generally two objects will connect to a patch panel pin - both of these objects are 'clients' of the panel.  The clients can either assert state on the pins, or simply read their values.  State is asserted by declaring either active high/low drive, passive pull-up (passive pull-down is unsupported), or tri-state (generally an input).  The patch panel arbitrates between the connected clients and declares the actual pin value, or declares that pin contention has occured.

The patch panel itself has no knowledge of the GPIO arrangement of any device.  It therefore works only in terms of it's own logical pin numbering.  For the Bifferboard, these logical pins are assigned as follows:

 Panel Pin
Bifferboard fuction
GPIO
 0
 LED 16
 1
 Button 15
 2
 J1 Pin2 TMS
 11
 3
 J1 Pin3 TDI
 13
 4
 J1 Pin4 TDO
 9
 5
 J1 Pin5 TCK
 12

The panel server must be started before any pins can be connected to.  It's started by running ./panel.py (see attachment below).  It can be stopped with CTRL-C.


Quick start
  • Download panel.py
  • Download led.py
  • Download button.py
  • Follow the above instructions but apply latest qemu-rdc-gpiopanel-0.10.5-X.patch to Qemu instead and use gpiolib-bzImage.
  • Open a terminal window and run ./panel.py
  • Open another terminal and run ./led.py
  • Open another terminal and run ./button.py
  • Run Qemu in a further terminal.
  • When Linux boots, set GPIO pin 16 as output via sysfs and you will see led.py respond when the LED state changes.
  • It should also be possible to read back the button state.

gpiolib-bzImage is a kernel image with gpiosysfs support compiled in.  You can program or read the GPIO pins via the sysfs interface as described here


The Qemu Panel client (qemu-0.10.5/hw/rdc-gpio.c)


In order for Qemu to connect to the Panel it must know how to talk to the panel, and which pin mappings to use.  This is achieved with a patch to Qemu which implements the Panel client code in C.  The GPIO mappings are defined in g_PinMap at the top of hw/rdc-gpio.c.  If the panel is not already running then Qemu will quit with an error on start-up.


The button client (button.py)


The button client is implemented in Python and simply opens a tkinter dialog and allows the user to change the button state (pin 1).



The LED client (led.py)


The LED client is also implemented in Python, and uses a class from the panel.py module (panel.py behaves as both a server and a client library).  The LED client is a text mode application and simply prints out the state of the LED when it changes.


In the screenshot above, the led is first connected to a Panel with no other clients.  It advertises itself as an input, so we are told that the LED is currently off, and given the reason.  In this case the LED input is considered tri-stated (X).  We then connect a button, which behaves as a pull-up resistor (P), since the button starts up in the 'not pressed' state.  Then the button is pressed, and the LED comes on (0, active drive low).  Next we release the button and it once more behaves as a simple pull-up (P).


HD44780 LCD display client (hd44780.py)

This emulates a simple 16 char x 2-line LCD display based on the popular Hitachi protocol. 6 panel lines are required (4 data and 2 control).  This has been implemented using pygtk, and requires lcdfont.py for the font bitmaps.


The display can be tested with lcdwrite.py.  It connects the server, and attempts to manipulate the GPIO pins to put text on the display.


All programs can be found in Subversion.



Attachments (4)

  • config-2.6.30.4 - on Aug 16, 2009 2:54 PM by bifferos ' (version 1)
    25k Download
  • gpiolib-bzImage - on Aug 31, 2009 4:08 PM by bifferos ' (version 1)
    914k Download
  • qemu-rdc-0.10.5-2.patch - on Aug 18, 2009 9:41 AM by bifferos ' (version 1)
    3k Download
  • qemu-rdc-gpiopanel-0.10.5.patch - on Sep 2, 2009 5:57 PM by bifferos ' (version 1)
    10k Download

Comments (1)

Andrew P Scheller - Sep 2, 2009 4:07 AM

"Linux still probes (and finds) an FPU, it would be good to disable this in Qemu"

In ./configure there's a CONFIG_SOFTFLOAT (which seems to be enabled for every arch other than x86!)
I tried forcing this to yes, but I then got compile errors related to the USE_X86LDOUBLE #define in target-i386/cpu.h (and different errors if I manually disabled the define), and I'm afraid that's as far as my low-level C knowledge goes... Does qemu 'allow' i386 to have softfloat?


Also, it looks like the qemu-rdc-gpiohub patch is missing the cpuid section of the qemu-rdc patch? (might it be better if they were non-overlapping patches?)