Offset address of Binary files - offset

I am using MPLAB to program ATSAMD20E15A. Now I have boot.bin and program.bin binray files generated.
My question is: How do I find the offset address of both these binary images?
Thank you and excuse me If the question is very basic since I am new to this.

The data sheet (page 265) says "The bootloader resides in the main array starting at offset zero." and appears to initially contain a factory programmed boot loader.
The boot loader code ends with a jump to the start of the runtime code which the program entry address must match.

Related

In Application Programming issue

I'm working on project on STM32L152RCT6, where i have to build a mechanism to self update the code from the newly gated file(HEX file).
For that i have implemented such mechanism like boot loader where it checks for the new firmware if there it it has to cross verify and if found valid it has to store on "Application location".
I'm taking following steps.
Boot loader address = 0x08000000
Application address = 0x08008000
Somewhere on specified location it has to check for new file through Boot loader program.
If found valid it has to be copy all the HEX on location(as per the guide).
Than running the application code through jump on that location.
Now problem comes from step 5, all the above steps I've done even storing of data has been done properly(verify in STM32 utility), but when i'm jump to the application code it won't work.
Is there i have to cross check or something i'm missing?
Unlike other ARM controllers that directly jump to address 0 at reset, the Cortex-M series takes the start address from a vector table. If the program is loaded directly (without a bootloader), the vector table is at the start of the binary (loaded or mapped to address 0). First entry at offset 0 is the initial value of the stack pointer, second entry at address 4 is called the reset vector, it contains the address of the first instruction to be executed.
Programs loaded with a bootloader usually preserve this arrangement, and put the vector table at the start of the binary, 0x08008000 in your case. Then the reset vector would be at 0x08008004. But it's your application, you should check where did you put your vector table. Hint: look at the .map file generated by the linker to be sure. If it's indeed at 0x08008000, then you can transfer control to the application reset vector so:
void (*app)(void); // declare a pointer to a function
app = *(void (**)(void))0x08008004; // see below
app(); // invoke the function through the pointer
The complicated cast in the second line converts the physical address to a pointer to a pointer to a function, takes the value pointed to it, which is now a pointer to a function, and assigns it to app.
Then you should manage the switchover to the application vector table. You can do it either in the bootloader or in the application, or divide the steps between them.
Disable all interrupts and stop SysTick. Note that SysTick is not an interrupt, don't call NVIC_DisableIRQ() on it. I'd do this step in the bootloader, so it gets responsible to disable whatever it has enabled.
Assign the new vector table address to SCB->VTOR. Beware that the boilerplate SystemInit() function in system_stm32l1xx.c unconditionally changes SCB->VTOR back to the start of the flash, i.e. to 0x08000000, you should edit it to use the proper offset.
You can load the stack pointer value from the vector table too, but it's tricky to do it properly, and not really necessary, the application can just continue to use the stack that was set up in the bootloader. Just check it to make sure it's reasonable.
Have you changed the application according to the new falsh position?
For example the Vector Table has to be set correctl via
SCB->VTOR = ...
When your bootloader starts the app it has to configure everything back to the reset state as the application may relay on the default reset values. Espessially you need to:
Return values of all hardware registers to its reset values
Switch off all peripheral clocks (do not forget about the SysTick)
Disable all enabled interrupts
Return all clock domains to its reset values.
Set the vector table address
Load the stack pointer from the beginning of the APP vector table.
Call the APP entry point.(vertor table start + 4)
Your app has to be compiled and linked using the custom linker script where the FLASH start point is 0x8008000
for example:
FLASH (rx) : ORIGIN = 0x8000000 + 32K, LENGTH = 512K - 32K
SCB->VTOR = FLASH_BASE | VECT_TAB_OFFSET;
where FLASH_BASE's value must be equal to the address of your IROM's value in KEIL
example:
#define FLASH_BASE 0x08004000
Keil configuration

How to get Device Instance Path from Windows kernel driver?

Take a look at this example: a USB device in Windows 7 is reported to have Device instance path(DevinstPath) USB\VID_1EAB&PID_0501\7&25C389C1&0&1 and I know exactly that it corresponds to the so-called hardware-key(hwkey) in registry.
Now my question is: When my KMDF driver code has WDFDEVICE handle for that USB device, how can I know its DevinstPath?
I know I can
send a BusQueryDeviceID to achieve the so-called device-id USB\VID_1EAB&PID_0501;
send a BusQueryInstanceID to achieve the so-called instance-id 1 .
But I don't know how to get the so-called "instance-path". Could some kernel guru kindly tell me how I can get that?
MSDN doc seems really vague on this!
BTW: I also realize that user-layer function SetupDiGetDeviceInstanceId actually returns the DevinstPath -- although it is named "InstanceId".
Device instance path can be queried using DEVPKEY_Device_InstanceId, using either WdfDeviceAllocAndQueryPropertyEx or IoGetDevicePropertyData (passing the WDM physical device object)
Device Instance id is autoincrement sequence.
You can find HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Enum in registry;
Rules:NextPareneID.XXXXXXXX.N
XXXXXX use UUID Calculation crc32 values(test ok)
N is 1~9
Device Instance id format is N&PareneID&random's number&index
enter image description here

Siemens S7-1200. TRCV_С. Error code: 893A; Event ID 02:253A

Please, help to solve the problem with communication establishment between PC and 1211C (6ES7-211-1BD30-0XB0 Firmware: V 2.0.2). I feel that I've made a stupid mistake somewhere, but can't figure out where exactly it is.
So, I'm using function TRCV_С...
The configuration seems to be okay:
When i set the CONT=1, the connection establishes without any problems...
But, when i set EN_R=1, I'm getting "error 893A".
That's what I have in my diagnostic buffer: (DB9 - is a block where the received data is supposed to be written)
There is an explanation given for "893A" in the manuals: Parameter contains the number of a DB that is not loaded. In diag. buffer its also written that DB9 is not loaded. But in my case it is loaded! So what should I do in this case?
it seems that DB were created or edited manually due to which they are miss aligned with FB instances try removing and DB and FB instances and then add again instances of FBs with automatically created DBs and do a offline dowonload

writing device driver in linux -- interupt handler

I am trying to write a loadable device driver.. which is capable to act on external event. please clarify following points.
1> modprob command is used to add remove modules to kernel. Does it applies to static modules ?
can modprobe or rmmod --- remove static module of linux kernel.
2> If interrupt comes i will save data & schedule the bottom half. Now when the bottom half completes its task how shall i inform application at user space that data is available.
3> I am thinking to use entry in debugfs to transfer data between application & driver. So is it feasible that my device driver & my user space application -- by using MAP() system call map same area of an file in debufs & exchange data between each other ?
modprob command is used to add remove modules to kernel. Does it applies to static modules ? can modprobe or rmmod --- remove static module of linux kernel.
If you mean by static module = a module that is compiled as part of the linux kernel (and not as a separate loadable module) then the answer is; no you cannot.
If interrupt comes i will save data & schedule the bottom half. Now when the bottom half completes its task how shall i inform application at user space that data is available.
If the user space app runs in polling mode, you can notify it by ioctl, or sysfs/procfs file. but if the user space app need to be notified in event-driver manner, then use netlink socket.
I am thinking to use entry in debugfs to transfer data between application & driver. So is it feasible that my device driver & my user space application -- by using MAP() system call map same area of an file in debufs & exchange data between each other ?
the way a user space app read/writes debugfs is by simply reading/writing the debugfs file (it's under /proc/.. or /sys/.., so you can "open" the file, get the file descriptor, then read/write - as if it was a regular file).

entry() get into the different address from the entry point I set in the Elf

Recently I'm learning about the OS. And I want to write a simple bootloader, which change the real mode to protect mode and then load the simple kernel.
But I can't figure out the entry address problem.
At first I put the bootloader in the first sector of the OS.img(qemu), and then the kernel begin at the second sector.
Here's readelf result of my kernel:
The entry point address is 0x800c.
And the LMA and VMA are below:
A part of the bootloader which read elf-type kernel and then get into the entry(),which is the entry point address.
However, when I disassemble the bootloader, the entry() is below:
Call *0x8018, not *0x800c.
I don't know why this happen.
Could you please help me?
call *0x8018 performs a call to an address that is stored at 0x8018, that's correct since ELFHDR is 0x8000 and offset of e_entry in the header is 0x18.
The real problem is in the way you load segments into memory. Each segment should be loaded at address p_vaddr from file offset p_offset. Notice that in your case p_vaddr is 0x8000, that the same place in memory you loaded elf header to and that's why ELFHDR->e_entry gets overwritten. The easiest solution would be to load elf header at different address.
Source: http://www.skyfree.org/linux/references/ELF_Format.pdf