Storing blocks on C arrays and running them later - objective-c

Ok, I can store blocks on NSArrays using something like this:
NSArray *myArray = #[[myBlock1 copy], [myBlock2 copy]];
and run that code later by doing, for example:
myBlockType runBlock = myArray[0];
runBlock(); // run baby, run
What about the C equivalent to this? Is that possible?

This works:
typedef void (^MyBlockType)(void);
MyBlockType blocks[100];
for(int i = 0; i < 100; i++) {
MyBlockType block= ^{printf("Run!");};
blocks[i] = block;
}
MyBlockType thisBlock = blocks[0];
thisBlock();

If the Operating System allows you to do that, you can assign the address of an array to a function pointer and call the code in the array using the name of that pointer.
typedef void (*fx_t)(void);
int main(void) {
fx_t udf;
unsigned char code[1000] = "<<machine code instructions>>";
udf = code; /* UB: assignment of object pointer to non-object pointer */
/* illegal assignment according to the Standard */
udf();
return 0;
}
As per requests in comments, here is a complete example that works on my computer (FreeBSD 9.2 on amd64)
#include <stdio.h>
#include <stdlib.h>
#include <sys/mman.h>
typedef int (*fx_t)(void);
int main(void) {
int a = -1;
fx_t udf;
unsigned char code[1000] = "\xb8\x2a\x00\x00\x00" // mov $0x2a,%eax
"\xc3"; // retq
void *codeaddr = code;
size_t length = 4096; /* size of a page */
if (mprotect(codeaddr, length, PROT_READ | PROT_WRITE | PROT_EXEC)) {
perror("mprotect");
exit(EXIT_FAILURE);
}
udf = (void*)code;
a = udf(); // call the code in the `code` string
printf("a is now %d.\n", a); // expect 42, changed by the code in `code`
code[1] = 24; // w00t! self changing code
a = udf();
printf("a is now %d.\n", a); // expect 24
return 0;
}
To get the bytes for my code, I compiled a very simple int fortytwo(void) { return 42; } to object file and then objdump -d it and tried the bytes that seemed relevant (I don't know assembly language)
0000000000000000 <fortytwo>:
0: 55 push %rbp
1: 48 89 e5 mov %rsp,%rbp
4: b8 2a 00 00 00 mov $0x2a,%eax
9: c9 leaveq
a: c3 retq
b: 0f 1f 44 00 00 nopl 0x0(%rax,%rax,1)

Related

Microblaze How to use AXI Stream?

I have a microblaze instantiated with 16 stream interfaces with a custom IP attached to two. What is the correct header file or function to communicate over these interfaces in Vitis (Not HLS)?
Based on the full example that you can find here, I am going to provide a general idea:
Include the mb_interface.h in your C source
Use the putfsl and getfsl macros to write and read from the stream.
Such macros are wrapper around special assembly instructions that the microblaze will execute by writing the data on the axi stream interface. The ìd is the stream id. Here you can find all the possible functions and here you can explore the ISA.
#define putfsl(val, id) asm volatile ("put\t%0,rfsl" stringify(id) :: "d" (val))
The fundamental issue is that
#include "mb_interface.h"
/*
* Write 4 32-bit words.
*/
static void inline write_axis(volatile unsigned int *a)
{
register int a0, a1, a2, a3;
a3 = a[3]; a1 = a[1]; a2 = a[2]; a0 = a[0];
putfsl(a0, 0); putfsl(a1, 0); putfsl(a2, 0); putfsl(a3, 0);
}
int main()
{
volatile unsigned int outbuffer[BUFFER_SIZE] = { 0x0, 0x1, 0x2, 0x3 }
};
/* Perform transfers */
write_axis(outbuffer);
return 0;
}

Raku how to pass a pointer to a Buf to a native call for writing

I'm trying to wrap the read function from unistd.h, but can't get it to work.
Here's what I have: (in file: read.raku)
use NativeCall;
# ssize_t read(int fd, void *buf, size_t count);
sub c_read(int32 $fd, Pointer $buf is rw, size_t $count --> ssize_t) is native is symbol('read') { * }
my $buf = Buf[byte].new(0 xx 5);
my $pbuf = nativecast(Pointer, $buf);
say c_read(3, $pbuf, 5);
say '---------------------';
say $buf;
I test it like this, from the command line (bash):
$ (exec 3< <(echo hello world); raku ./read.raku)
But I get:
5
---------------------
Buf[byte]:0x<00 00 00 00 00>
So it looks like the bytes read from FD 3 are not written to the Buf.
I also tried this instead:
use NativeCall;
# ssize_t read(int fd, void *buf, size_t count);
sub c_read(int32 $fd, Pointer $buf is rw, size_t $count --> ssize_t) is native is symbol('read') { * }
sub c_malloc(size_t $size --> Pointer) is native is symbol('malloc') { * }
my $pbuf = nativecast(Pointer[byte], c_malloc(5));
say c_read(3, $pbuf, 5);
say '---------------------';
say $pbuf[^5];
But I get a segmentation fault, I guess due to dereferencing into unauthorized memory location with $pbuf[^5]. But even just $pbuf.deref doesn't give the first byte read.
So I must have done something wrong or completely misunderstood how to work with native calls.
UPDATE:
After playing around with it more, it looks like the problem with the second snippet above is with the is rw bit. This seems to work:
use NativeCall;
use NativeHelpers::Blob;
sub c_read(int32 $fd, Pointer $buf, size_t $count --> ssize_t) is native is symbol('read') { * }
sub c_malloc(size_t $size --> Pointer) is native is symbol('malloc') { * }
my $pbuf := nativecast(Pointer[byte], c_malloc(5));
say c_read(3, $pbuf, 5);
say '---------------------';
say $pbuf[^5]; # (104 101 108 108 111)
OK, so the problem is with the rw trait given to the Pointer $buf. I guess that results in the read function incrementing the pointer as it writes, and thus gives the wrong address when I use it later.
Here's the working code for both cases:
use NativeCall;
# ssize_t read(int fd, void *buf, size_t count);
sub c_read(int32 $fd, Pointer $buf, size_t $count --> ssize_t) is native is symbol('read') { * }
# Passing a pointer to a Buf directly:
{
my $buf = Buf[byte].new(0 xx 5);
my $pbuf = nativecast(Pointer[byte], $buf);
say c_read(3, $pbuf, 5);
say '---------------------';
say $buf;
}
# Using malloc also works:
{
sub c_malloc(size_t $size --> Pointer) is native is symbol('malloc') { * }
my $pbuf = nativecast(Pointer[byte], c_malloc(5));
say c_read(3, $pbuf, 5);
say '---------------------';
say $pbuf[^5];
}
Tested it like this:
$ (exec 3< <(echo hello world); perl6 ./read.raku)
5
---------------------
Buf[byte]:0x<68 65 6C 6C 6F>
5
---------------------
(32 119 111 114 108)

InterruptAttach fails on am3352x irq number 97 for bank 0B

I am trying to attach an IRQ handler to a gpio bank 0 i.e 0B irq no 97.
At the present moment, my implementation returns with -1. What am I doing wrong? It would be a very simple issue to implement.
#include <stdio.h>
#include <unistd.h>
#include "gpio.h"
#include <sys/neutrino.h>
#include "interrupt.h"
volatile unsigned int gpio0_irq_count;
static const struct sigevent * gpio0_irq_handler (void *gpio, int id){
gpio0_irq_count++;
return NULL;
}
int main(){
int ret;
unsigned long count=0;
ret = InterruptAttach(97, gpio0_irq_handler, NULL,0,_NTO_INTR_FLAGS_TRK_MSK);
printf("%s: Registering handler for irq %d result = %d\n",__func__ , 97, ret);
if (ret)
return -1;
while(1){
printf("%s:[%lu] : gpio0_irq_count = %d\n", __func__, count++, gpio0_irq_count);
sleep(2);
}
}
The erroneous output is:
main: Registering handler for irq 97 result = -1
After much back and forth with QNX, it turns out that a process requesting InterruptAttach() or InterruptAttach_r() needs elevated permissions acquired through
ThreadCtl( _NTO_TCTL_IO, 0 );
Once that is executed the API's work. However, one must still configure the gpio registers to actually fire the interrupt.
GPIO_OE
GPIO_STATUS
GPIO_STATUS_SET
GPIO_CTRL
GPIO_RISINGDETECT

Arm loop code optimization for calculating mean standard deviation

I want to improve some code which is using 25% of my app CPU, the code is the next:
for (int i=0; i<8; i++) {
unsigned f = *p++;
sum += f;
sqsum += f*f;
}
I made some arm code but it is not working, even not compiling, which is the next:
void loop(uint8_t * p , int * sum ,int * qsum)
{
__asm__ volatile("vld4.8 {d0}, [%0]! \n"
"mov r4, #0 \n"
"vmlal.u8 [%1]!, [%1]!, d0 \n"
"vmull.u8 r4, d0 , d0 \n"
"vmlal.u8 [%2]!, [%2]!, r4\n"
:
: "r"(p), "r"(sum), "r"(qsum)
: "r4"
);
}
Any help?
Here is the my function to improve:
void calculateMeanStDev8x8(cv::Mat* patch, int sx, int sy, int& mean, float& stdev)
{
unsigned sum=0;
unsigned sqsum=0;
for (int j=0; j< 8; j++) {
const unsigned char* p = (const unsigned char*)(patch->data + (j+sy)*patch->step + sx); //Apuntador al inicio de la matrix
//The code to improve
for (int i=0; i<8; i++) {
unsigned f = *p++;
sum += f;
sqsum += f*f;
}
}
mean = sum >> 6;
int r = (sum*sum) >> 6;
stdev = sqrtf(sqsum - r);
if (stdev < .1) {
stdev=0;
}
}
That loop is a perfect candidate for NEON optimization. You can fit your 8 unsigned integers into a single NEON register. There is no "sum all elements of a vector" instruction, but you can use the pairwise add to compute the sum of the 8 elements in 3 steps. Since we can't see the rest of your application, it's hard to know what the big picture is, but NEON is your best bet for improving the speed. All recent Apple products support NEON instructions and in XCode you can use the NEON intrinsics mixed with your C++ code.

Using IOKit to return Mac's Serial number returns 4 extra characters

I'm playing with IOKit and have the following code, the general idea is to pass a platformExpert key to this small core foundation command line application and have it print the decoded string. The test case is "serial-number". The code below when run like:
./compiled serial-number
Almost works but returns the last 4 characters of the serial number at the beginning of the string i.e. for an example serial such as C12D2JMPDDQX it would return
DDQXC12D2JMPDDQX
Any ideas?
#include <CoreFoundation/CoreFoundation.h>
#include <IOKit/IOKitLib.h>
int main (int argc, const char * argv[]) {
CFStringRef parameter = CFSTR("serial-number");
if (argv[1]) {
parameter = CFStringCreateWithCString(
NULL,
argv[1],
kCFStringEncodingUTF8);
}
CFDataRef data;
io_service_t platformExpert = IOServiceGetMatchingService(kIOMasterPortDefault, IOServiceMatching("IOPlatformExpertDevice"));
if (platformExpert)
{
data = IORegistryEntryCreateCFProperty(platformExpert,
parameter,
kCFAllocatorDefault, 0);
}
IOObjectRelease(platformExpert);
CFIndex bufferLength = CFDataGetLength(data);
UInt8 *buffer = malloc(bufferLength);
CFDataGetBytes(data, CFRangeMake(0,bufferLength), (UInt8*) buffer);
CFStringRef string = CFStringCreateWithBytes(kCFAllocatorDefault,
buffer,
bufferLength,
kCFStringEncodingUTF8,
TRUE);
CFShow(string);
return 0;
}
A more simplified solution:
#include <CoreFoundation/CoreFoundation.h>
#include <IOKit/IOKitLib.h>
int main()
{
CFMutableDictionaryRef matching = IOServiceMatching("IOPlatformExpertDevice");
io_service_t service = IOServiceGetMatchingService(kIOMasterPortDefault, matching);
CFStringRef serialNumber = IORegistryEntryCreateCFProperty(service,
CFSTR("IOPlatformSerialNumber"), kCFAllocatorDefault, 0);
const char* str = CFStringGetCStringPtr(serialNumber,kCFStringEncodingMacRoman);
printf("%s\n", str); //->stdout
//CFShow(serialNumber); //->stderr
IOObjectRelease(service);
return 0;
}
compile with:
clang -framework IOKit -framework ApplicationServices cpuid.c -o cpuid
Fork from github if you like ;)
https://github.com/0infinity/IOPlatformSerialNumber
You may be misinterpreting the value of the serial-number parameter. If I use ioreg -f -k serial-number, I get this:
| "serial-number" =
| 00000000: 55 51 32 00 00 00 00 00 00 00 00 00 00 XX XX XX XX UQ2..........XXXX
| 00000011: XX XX XX XX 55 51 32 00 00 00 00 00 00 00 00 00 00 XXXXUQ2..........
| 00000022: 00 00 00 00 00 00 00 00 00 .........
(I've X'd out my Mac's serial number except for the repeated part.)
You don't see the null characters when you show the string because, well, they're null characters. I don't know why it has what seems like multiple fields separated by null characters, but that's what it seems to be.
I recommend doing further investigation to make sure there isn't a specification for how this data is supposed to be interpreted; if you don't find anything, I'd skip through the first run of nulls and get everything after that up to the next run of nulls.