I have structure that contains two fields:
struct ggg {
unsigned long long int a;
unsigned int b;
};
Field a should be 8 bytes long, while b one is 4 bytes long.
Trying to cast it to array of bytes:
unsigned char c[8 + 4] = { 0x01, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00,
0x03, 0x00, 0x00, 0x00, };
ggg* g = (ggg *)c ;
char tt[1024];
sprintf(tt, "a=%d b=%d ", g->a, g->b);
Got result in tt string :
a=1 b=2
Looks like while casting a takes only 4 bytes instead of 8. Why?
The problem is not casting but your sprintf format specifiers. You are using %d which means signed int, which typically is 4 bytes.
Try changing the format string to "a=%llu b=%u" and you are more likely to get the expected output.
As starting point I have a method that works. But it seems to have too many lines or overlapping actions.
If you are audio wizard then you see immediately how to boil this down. So how to boil this down?
public static byte[] float16toDualByte(byte[] twoPlaces, float f_val) {
short val_as_short = (short) (f_val * 32768);//signed short.16bit.
twoPlaces[0] = (byte) (val_as_short >>> 8);
twoPlaces[1] = (byte) val_as_short;
ByteBuffer buf = ByteBuffer.wrap(twoPlaces);
buf.order(ByteOrder.LITTLE_ENDIAN);
short turned = buf.asShortBuffer().get(0);
twoPlaces[0] = (byte) (turned >>> 8);
twoPlaces[1] = (byte) turned;
return twoPlaces;
}
I found at sof the idea that turn upscaled float first to int. And it worked!
This method gives array of two bytes ready to write into javax.sound.sampled.SourceDataLine. Those two bytes represent one mono frame.
One thing to understand with SourceDataLine is that name is given from the physical soundcard standpoint. That little man inside soundcard waiting to pass sample to connector. From user perspective it means the output to soundcard.
public byte[] simpleSwap(byte[] twoPlaces, float f_val) {
int val_as_short = (int) (f_val * 32768);//signed short.16bit as int.
int swapped = ((val_as_short >> 8) & 0xff) | ((val_as_short & 0xff) << 8);
twoPlaces[0] = (byte) (swapped >>> 8);
twoPlaces[1] = (byte) swapped;
return twoPlaces;
}
I have used the linux 3.14 version on my ARM target and i want to show some line of characters in the display using frame buffer. I can change the colors of the display using the below code.
#include <stdio.h>
unsigned char colours[8][4] = {
{ 0x00, 0xFF, 0x00, 0xFF }, // green
{ 0x00, 0xFF, 0x00, 0xFF }, // green
{ 0x00, 0xFF, 0x00, 0xFF }, // green
{ 0x00, 0xFF, 0x00, 0xFF }, // green
{ 0x00, 0xFF, 0x00, 0xFF }, // green
{ 0x00, 0xFF, 0x00, 0xFF }, // green
{ 0x00, 0xFF, 0x00, 0xFF }, // green
{ 0x00, 0xFF, 0x00, 0xFF }, // green
};
int frames[] = {0,5,10,15,20,25,30};
int columns = 800;
int lines = 480;
#define ARRAY_SIZE(a) (sizeof(a)/sizeof(a[0]))
int frame(int c, int l){
int i;
for(i=0; i < ARRAY_SIZE(frames); i++){
if((c==frames[i])&&((l>=frames[i])&&l<=(lines-frames[i]))){
return 1;
}
if((c==columns-frames[i])&&((l>=frames[i])&&l<=(lines-frames[i]))){
return 1;
}
if((l==frames[i])&&((c>=frames[i])&&c<=(columns-frames[i]))){
return 1;
}
if((l==lines-frames[i])&&((c>=frames[i])&&c<=(columns-frames[i]))){
return 1;
}
}
return 0;
}
int main(int argc, char **argv)
{
unsigned char pixel[3];
int l, c;
char *filename = argv[1];
printf ("Device : %s\n",filename);
FILE *f = fopen(filename,"wb");
if(f){
printf("Device open success \n");
for(l=0; l<lines; l++){
for(c=0; c < columns; c++){
if(frame(c,l)){
fwrite(colours[3], 1, sizeof(colours[3]), f);
}else{
int colour = c/(columns/ARRAY_SIZE(colours));
fwrite(colours[colour], 1, sizeof(colours[colour]), f);
}
}
}
fclose(f);
}
else
printf("Device open failed \n");
return 0;
}
In the same way i want to show some lines of character to the display. Example, I want to show characters "Hello world !!!" in the display using frame buffer.
Could any one help me to work it out.
You can find an elegant piece of code to do this in tslib. tslib is a c library for filtering touchscreen events. Actually, you don't need tslib for your purpose (yes, you don't have to build it). In their tests you can find a utility to access the framebuffer.
They have provided the fbutils.h whose implementation you can find in fbutils-linux.c. This code is very simple in that it directly manipulates the linux framebuffer and does not have any dependencies. Currently it's not even 500 lines, and if you only want to display text, you can remove other irrelevant functionality. It supports two fonts - font_8x8 and font_8x16 - whose definitions you can find in the respective .c files.
I won't go into code details as it is easy to understand. Will just list the current API and provide a simpler code for open and close functionality.
int open_framebuffer(void);
void close_framebuffer(void);
void setcolor(unsigned colidx, unsigned value);
void put_cross(int x, int y, unsigned colidx);
void put_string(int x, int y, char *s, unsigned colidx);
void put_string_center(int x, int y, char *s, unsigned colidx);
void pixel(int x, int y, unsigned colidx);
void line(int x1, int y1, int x2, int y2, unsigned colidx);
void rect(int x1, int y1, int x2, int y2, unsigned colidx);
void fillrect(int x1, int y1, int x2, int y2, unsigned colidx);
To manipulate the linux framebuffer, first you should memory map it into your process address space. After memory mapping you can access it just like an array. Using some ioctl you can get information about the framebuffer such as resolution, bytes-per-pixel etc. See here for details.
In the code below, you can pass the name of the fb device to open it, such as /dev/fb0. You can use the rest of the functions in the original code for drawing.
int open_framebuffer(const char *fbdevice)
{
uint32_t y, addr;
fb_fd = open(fbdevice, O_RDWR);
if (fb_fd == -1) {
perror("open fbdevice");
return -1;
}
if (ioctl(fb_fd, FBIOGET_FSCREENINFO, &fix) < 0) {
perror("ioctl FBIOGET_FSCREENINFO");
close(fb_fd);
return -1;
}
if (ioctl(fb_fd, FBIOGET_VSCREENINFO, &var) < 0) {
perror("ioctl FBIOGET_VSCREENINFO");
close(fb_fd);
return -1;
}
xres_orig = var.xres;
yres_orig = var.yres;
if (rotation & 1) {
/* 1 or 3 */
y = var.yres;
yres = var.xres;
xres = y;
} else {
/* 0 or 2 */
xres = var.xres;
yres = var.yres;
}
fbuffer = mmap(NULL,
fix.smem_len,
PROT_READ | PROT_WRITE, MAP_FILE | MAP_SHARED,
fb_fd,
0);
if (fbuffer == (unsigned char *)-1) {
perror("mmap framebuffer");
close(fb_fd);
return -1;
}
memset(fbuffer, 0, fix.smem_len);
bytes_per_pixel = (var.bits_per_pixel + 7) / 8;
transp_mask = ((1 << var.transp.length) - 1) <<
var.transp.offset; /* transp.length unlikely > 32 */
line_addr = malloc(sizeof(*line_addr) * var.yres_virtual);
addr = 0;
for (y = 0; y < var.yres_virtual; y++, addr += fix.line_length)
line_addr[y] = fbuffer + addr;
return 0;
}
void close_framebuffer(void)
{
memset(fbuffer, 0, fix.smem_len);
munmap(fbuffer, fix.smem_len);
close(fb_fd);
free(line_addr);
xres = 0;
yres = 0;
rotation = 0;
}
You can find examples of its usage in test programs in the folder, such as ts_test.c.
You can extend this code to support other fonts, display images etc.
Good luck!
First, I strongly suggest to avoid use of fopen/fwrite function to access devices. These function handle internal buffers that can be troublesome. Prefers functions open and write.
Next, you can't continue with series of if .. then .. else .. to render a true graphic. You need to allocate a buffer that represent your framebuffer. Its size will, be columns * lines * 4 (you need 1 byte per primary color). To write a pixel, you have to use something like:
buf[l * columns + c * 4 + 0] = red_value;
buf[l * columns + c * 4 + 1] = green_value;
buf[l * columns + c * 4 + 2] = blue_value;
buf[l * columns + c * 4 + 3] = alpha_value;
Once you buffer is fully filled, write it with:
write(fd, buf, sizeof(buf));
(where fd is file descriptor return by fd = open("/dev/fbdev0", O_WRONLY);)
Check that you are now able to set arbitrary pixels on our framebuffer.
Finally, you need a database of rendered characters. You could create it yourself, but I suggest to use https://github.com/dhepper/font8x8.
Fonts are monochrome so each bit represent one pixel. On your framebuffer, you need 4bytes for one pixel. So you will have to do some conversion.
This is a really basic way to access framebuffer, there are plenty of improvements to do:
columns, lines and pixel representation should negotiated/retrieved using FBIO*ET_*SCREENINFO ioctl.
using write to access framebuffer is not the preferred method. It is slow and does not allow to updating framebuffer easily. The preferred method use mmap.
if you want to to animate framebuffer, you to use a double buffer: allocate a buffer twice larger than necessary, write alternatively first part or second part and update shown buffer with FBIOPAN_DISPLAY
font8x8 is not ideal. You may want to use any other font available on web. You need a library to decode font format (libfreetype) and a library to render a glyph (= a letter) in a particular size to a buffer (aka rasterize step) that you can copy to your screen (libpango)
you may want to accelerate buffer copy between your glyph database and your screen framebuffer (aka compose step), but it is a far longer story that involve true GPU drivers
In the core bluetooth 4.2 documentation here it talks about a CRC check for data integrity (P2456). This details the below:
With an example below:
4e 01 02 03 04 05 06 07 08 09
Producing CRC: 6d d2
I have tried a number of different methods but can't seem to reproduce the example. Can anyone provide some sample code to produce the CRC above.
You left out a key part of the example in the document, which is that the UAP used in the example is 0x47. The CRC needs to be initialized with the UAP. (Oddly, with the bits reversed and in the high byte, relative to the data bits coming in.)
The code below computes the example. The result is d26d. The CRC is transmitted least significant bit first, so it is sent 6d d2. On the receive side the same CRC is computed on the whole thing with the CRC, and the result is zero, which is how the receive side is supposed to check what was sent.
#include <stdio.h>
static unsigned crc_blue(unsigned char *payload, size_t len) {
unsigned crc = 0xe200; // UAP == 0x47
while (len--) {
crc ^= *payload++;
for (int k = 0; k < 8; k++)
crc = crc & 1 ? (crc >> 1) ^ 0x8408 : crc >> 1;
}
return crc;
}
int main(void) {
unsigned char payload[] = {
0x4e, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09};
printf("%04x\n", crc_blue(payload, sizeof(payload)));
unsigned char recvd[] = {
0x4e, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x6d, 0xd2};
printf("%04x\n", crc_blue(recvd, sizeof(recvd)));
return 0;
}
Your code would need to initialize the UAP appropriately for that device.
I have a BYTE data[3]. The first element, data[0] has to be a BYTE with very specific values which are as follows:
typedef enum
{
SET_ACCURACY=0x01,
SET_RETRACT_LIMIT=0x02,
SET_EXTEND_LIMT=0x03,
SET_MOVEMENT_THRESHOLD=0x04,
SET_STALL_TIME= 0x05,
SET_PWM_THRESHOLD= 0x06,
SET_DERIVATIVE_THRESHOLD= 0x07,
SET_DERIVATIVE_MAXIMUM = 0x08,
SET_DERIVATIVE_MINIMUM= 0x09,
SET_PWM_MAXIMUM= 0x0A,
SET_PWM_MINIMUM = 0x0B,
SET_PROPORTIONAL_GAIN = 0x0C,
SET_DERIVATIVE_GAIN= 0x0D,
SET_AVERAGE_RC = 0x0E,
SET_AVERAGE_ADC = 0x0F,
GET_FEEDBACK=0x10,
SET_POSITION=0x20,
SET_SPEED= 0x21,
DISABLE_MANUAL = 0x30,
RESET= 0xFF,
}TYPE_CMD;
As is, if I set data[0]=SET_ACCURACY it doesn't set it to 0x01, it sets it to 1, which is not what I want. data[0] must take the value 0x01 when set it equal to SET_ACCURACY. How do I make it so that it does this for not only SET_ACCURACY, but all the other values as well?
EDIT: Actually this works... I had a different error in my code that I attributed to this. Sorry!
Thanks!
"data[0]=SET_ACCURACY doesn't set it to 0x01, it sets it to 1"
It assigns value of SET_ACCURACY to the data[0], which means that bits 00000001 are stored into memory at address &data[0]. 0x01 is hexadecimal representation of this byte, 1 is its decimal representation.