Secondary bootloader for NXP LPC1114/5
Reference NXP app note 10995
Need to use same interrupts in bootloader and user application.
According to NXP AN10995, int vector is only at location 0, and no vector offset reg is available offsetting to other int vector. According to app note, secondary bootloader must redirect processor to handler in user application flash.
Problem/question I have -user application flash will be overwritten during firmware update, so not possible to locate handler there. What is recommended approach, when interrupt will be used by bootloader and user application.
Does this require a conditional redirect, based on the application running (bootloader/user application), such as 1) if bootloader running, re-direct to int handler in bootloader area, 2) if user app running, re-direct to int. handler in user app, or 3) use shared memory between bootloader and user app?
I've coded many boot loaders / firmware upgrades. If you cannot change the interrupt vectors you need to use polled code, i.e.
Copy the firmware upgrader to RAM, or make sure it's located in an area of FLASH that will not be erased
It's likely that the setup for say the UART is already setup to use interrupts, you need to reconfigure all required hardware to use polled methods, i.e. no interrupts.
Disable Interrupts !
Jump to the firmware upgrade function
The firmware upgrade function will not return, it will poll for messages via the UART and erase, program, verify flash section at the request of the client application.
DO NOT ENABLE INTERRUPTS!
When finished, you can reset the Processor using the watchdog to reboot it and execute the new code.
Related
I want to make my development board's bootloader (which is u-boot) be locked so no one can stop autoboot process at all. (In this way I will be sure that no one can alter the firmware of the board!)
So please guide me in order to locking the firmware and block any "root" attempts. I am using amlogic s905x SoC.
Another question:
Is this process relates to verified boot and signing kernel images?
If your SoC chip supports secure boot, then it is a way to make its firmware, secure of jail breaking. consult the datasheet. Otherwise you can not 'lock' the firmware.
You can use CONFIG_AUTOBOOT_KEYED=Password to require a password for stopping autoboot.
You can use CONFIG_BOOTDELAY=-2 to autoboot with no delay and not check for abort.
This will not stop users with physical access from altering the firmware. They could simply insert there own SD-card or USB stick or reprogram the eMMC.
CONFIG_AUTOBOOT_KEYED will make you live easier if you need to reflash a returned device.
This is a hypothetical question. Suppose there is an application (which typically executes in user mode) that wants to access kernel data structures, read register values, and perform some kernel-level functions.
Is there a way for kernel and/or CPU to allow this application to perform its functions while maintaining the normal user-level/kernel-level isolation for other applications except this one?
In order to either put your app in kernel space (kernel memory) or to run it in ring 0 CPU mode, you will need to do that from kernel code. In normal state of operation you can't run app from the kernel with mentioned privileges (at least there is no existing API to do that). It's probably possible to implement some kernel code which is able of this. But it will be tricky and will mess up the whole concept of kernel-space/user-space separation, and if any advanced user-space API was used -- it won't work anyway.
If you are thinking about just giving your app ring 0 privileges -- it won't work either, because kernel has its own stack and because of kernel-space/user-space memory separation, so you won't be able to run internal kernel API.
Basically, you can achieve the same thing by writing kernel module instead. And for running some kernel code on behalf of user-space app -- you can use system calls interface.
So, answering your question: no, it's not possible to run user-space app in kernel mode so it can use internal kernel API.
From a general standpoint, I am trying to figure out how to access a platform device from userspace. To be more specific, I have a EMIF controller on and SoC of which I have added to my device tree and I believe it is correctly bound to a pre-written EMIF platform device driver. Now I am trying to figure out how I can access this EMIF device from a userspace application. I have come accross a couple different topics that seem to have some connection to this issue but I cannot quite find out how they relate.
1) As I read it seems like most I/O is done through the use of device nodes which are created by mknod(), do I need to create a device node in order to access this device?
2) I have read a couple threads that talk about writting a Kernel module (Character?, Block?) that can interface with both userspace and the platform device driver, and use it as an intermediary.
3) I have read about the possibility of using mmap() to map the memory of my platform device into my virtual memory space. Is this possible?
4) It seems that when the EMIF driver is instantiated, it calls the probe() fucntion. What functions would a userpace application call in the driver?
It's not completely clear what you're needing to do (and I should caveat that I have no experience with EMIF or with "platform devices" specifically), but here's some overview to help you get started:
Yes, the usual way of providing access to a device is via a device node. Usually this access is provided by a character device driver unless there's some more specific way of providing it. Most of the time if an application is talking "directly" to your driver, it's a character device. Most other types of devices are used in interfacing with other kernel subsystems: for example, a block device is typically used to provide access from a file system driver (say) to an underlying disk drive; a network driver provides access to the network from the in-kernel TCP/IP stack, etc.
There are several char device methods or entry points that can be supported by your driver, but the most common are "read" (i.e. if a user-space program opens your device and does a read(2) from it), "write" (analogous for write(2)) and "ioctl" (often used for configuration/administrative tasks that don't fall naturally into either a read or write). Note that mknod(2) only creates the user-space side of the device. There needs to be a corresponding device driver in the kernel (the "major device number" given in the mknod call links the user-space node with the driver).
For actually creating the device node in the file system, this can be automated (i.e. the node will automatically show up in /dev) if you call the right kernel functions while setting up your device. There's a special daemon that gets notifications from the kernel and responds by executing the mknod(2) system call.
A kernel module is merely a dynamically loadable way of creating a driver or other kernel extension. It can create a character, block or network device (et al.), but then so can a statically linked module. There are some differences in capability mostly because not all kernel functions you might want to use are "exported" to (i.e. visible to) dynamically loaded modules.
It's possible to support mapping of the device memory into user virtual memory space. This would be implemented by yet another driver entry point (mmap). See struct file_operations for all the entry points a char driver can support.
This is pretty much up to you: it depends on what the application needs to be able to do. There are many drivers in the kernel that provide no direct function to user-space, only to other kernel code. As to "probe", there are many probe functions defined in various interfaces. In most cases, these are called by the kernel (or perhaps by a 'higher level "class" driver') to allow the specific driver to discover, identify and "claim" individual devices. They (probe functions) don't usually have anything directly to do with providing access from user-space but I might well be missing something in a particular interface.
You need to create a device node in order to access the device.
The probe function is called when the driver finds a matching device.
For information on platform device API, the following articles could be useful.
The platform device API
Platform devices and device trees
I have a Windows XP application that is using a driver called TVicHW32 which allows me to create an interrupt handler for OS interrupts. Currently I am using a custom ISA card in an industrial chassis with IRQ 5
The interrupt handler code is working and I can see a variable being incremented so the code that sets up and handles the interrupt is working.
The issue I have is that an IO access call fails to generate any IO activity on the ISA bus. I have an address at 0x308 that is used to trigger a start pulse on the ISA bus interface board.
If I trigger this pulse from the main code, for example, from a timer, the pulse is detected on the ISA bus and the card responds.
If I call the exact same function call to access that IO address from within the interrupt handler, nothing appears on the ISA bus. A logic analyser confirms this.
I have emailed the supplier of the driver but that can't help so I was wondering if anyone here has come across this situation and can offer a solution. This is critical to getting this project working and the only solution I can think of is to develop a custom driver with the DDK but as this requires a steep learning curve, I would hope to find an alternative solution.
Thanks
Dave...
I'd like to call my app from my driver when an interesting event happens in the Windows kernel. I need to be able to pass at least 4 bytes of data back to user mode. How to achieve this? These events might happen quite, but not too, often, so I don't want to build a queue system and use IOCTLs.
I was thinking of something like the driver gets loaded, the user mode app registers its callback using IOCTL and kernel keeps calling that callback when events happen and finally the user mode client unregisters the callback and no more data is send to user mode. Is this possible?
I'm new to kernel programming, so after a day of googling I decided to ask here. I've noticed that there isn't much discussion about the kernel and drivers. And even less proper docs.