What I do is
Get address of ExitProcess
Make space for opcode
Modify opcode in the space
Execute modified opcode by __asm__ ("jmp %%ecx"::"c"(opcode));
Here is my code:
#include <windows.h>
#include <stdio.h>
int main()
{
char addr[4];
*(int*)addr = GetProcAddress(GetModuleHandle("kernel32.dll"),"ExitProcess");
//push 0 == 0x6a 0x00
//call ExitProcess == 0xe8 0xd8 0x79 0xa2 0x75
char opcode[400] = {0x6a, 0x00, 0xe8,addr[0], addr[1],addr[2],addr[3]};
__asm__ ("jmp %%ecx" ::"c"(opcode));
//never be here
printf("never get here");
getchar();
return 0;
}
I expect program to exit normally, but the program terminates with a segmentation fault.
It seems that it jumps to somewhere, but not to the location I want it to jump.
How can I fix that?
Setting aside the odd thing you are trying to do...
Your problem is the opcode e8 is a relative jump. So you need to account for the address you are storing it at. Something like this maybe:
Update: Per taeyun, account for length of x.
#include <windows.h>
#include <stdio.h>
#pragma pack(1)
struct mfoo {
unsigned char x[3] = {0x6a, 0x00, 0xe8};
void *addr;
} foo;
int main()
{
unsigned char *a = (unsigned char *)GetProcAddress(GetModuleHandle("kernel32.dll"),"ExitProcess");
foo.addr = (void *)(a - sizeof(foo) - (unsigned char *)foo.x);
__asm__ ("jmp *%%ecx" ::"c"(&foo));
//never be here
printf("never get here");
getchar();
return 0;
}
Related
This my Mod bus crc_16 embedded code. I have run this code in code block many Times. There is no error but I am not getting actual crc value. I should get crc 05C8 and I am getting 8512 right now.
I think I giving wrong input while calling CRC method. I am passing string and its length. So please help me.
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#define POLY 0x8005
unsigned int ModRTU_CRC(unsigned char * mod_data,unsigned int length)
{
unsigned int CRC16 = 0xFFFF;
unsigned int pos=0,i=0;
for(pos=0;pos<length;pos++)
{
CRC16 ^= (unsigned int) mod_data[pos];
for(i=0;i<8;i++)
{
if((CRC16 & 0x0001)!=0)
{
CRC16 >>=1;
CRC16^=0xA001;
}
else
{
CRC16 >>=1;
}
}
}
return CRC16;
}
int main()
{
//char *frame = "010600081388";
// char *frame = "010300080001";
char frame[7];
frame[0]=0x01;
frame[1]=0x03;
frame[2]=0x00;
frame[3]=0x08;
frame[4]=0x00;
frame[5]=0x01;
frame[6]='\0';
printf("%x\n",frame);
int len = strlen(frame);
unsigned int crcv = ModRTU_CRC(frame,len);
printf("%x\n",crcv);
return 0;
}
The bug is that in your original code you used frame[2]=0x00; followed by strlen(), which will interpret this as the null terminator and give the wrong size 2 instead of 6. You cannot use strlen() on binary data.
In the "fixed" version you hard-code the size to 6 so the bug was removed by accident. It has nothing to do with uint8_t versus char (although it is always better to use uint8_t for binary data).
#include <stdint.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#define POLY 0x8005
unsigned int ModRTU_CRC(unsigned char * mod_data,unsigned int length)
{
unsigned int CRC16 = 0xFFFF;
unsigned int pos=0,i=0;
for(pos=0;pos<length;pos++)
{
CRC16 ^= (unsigned int) mod_data[pos];
for(i=0;i<8;i++)
{
if((CRC16 & 0x0001)!=0)
{
CRC16 >>=1;
CRC16^=0xA001;
}
else
{
CRC16 >>=1;
}
}
}
return CRC16;
}
int main()
{
uint8_t message[80] = { // 6-byte test vector
0x01, 0x03, 0x00, 0x08, 0x00, 0x01
};
int message_length = 6;
printf("%x\n",message);
// int len = strlen(message);
uint16_t the_CRC = ModRTU_CRC(message,message_length);
printf("%x\n",the_CRC);
return 0;
}
`
I have 2 defines, one with a string and one with a number.How can i make a const array from the define with the string and the number. There are also some additional constant which should be in this array.
How can i write this Code to have 0x22, 0x41, 0x42, 0x42, 0x21 in the array foobar, from the defines FOO and BAR?
#define FOO "AB"
#define BAR 33
extern int rs232_write(const unsigned char *data, unsigned char count);
const unsigned char foobar[] =
{
0x22,
FOO[0], /*what must i put here, this do not work*/
FOO[1],
0x42,
BAR,
};
int main(void)
{
rs232_write(foobar,sizeof(foobar));
return 1;
}
In gcc, for example, i get the error:
./001.c:9:5: error: initializer element is not constant
FOO[0], /*what must i put here*/
^
The String have always the same length.
I did also a try the other way around:
#define FOO "AB"
#define BAR 33
extern int rs232_write(const unsigned char *data, unsigned char count);
const char foobar[] = \
"\x22" \
FOO \
"\x42" \
BAR /*what must i put here, this also not work*/
int main(void)
{
rs232_write(foobar,sizeof(foobar));
return 1;
}
Here i get also a error, for example gcc prints:
./002.c:2:13: error: expected ‘,’ or ‘;’ before numeric constant
#define BAR 33
^
I working on a Microcontroller with not much space, so i would like to avoid creating the array at runtime and my compiler do only support C89.
The simplest, using memcpy:
#include <stdio.h>
#include <string.h>
#define FOO "AB"
#define BAR 33
extern int rs232_write(const unsigned char *data, unsigned char count);
unsigned char _foobar[] =
{
0x22,
0, 0,
0x42,
BAR,
};
const unsigned char *foobar;
int main(void)
{
foobar = (const unsigned char *)memcpy(_foobar + 1, FOO, 2) - 1;
rs232_write(foobar,sizeof(foobar));
return 0;
}
The ugly, using an X Macro and a compound literal:
In this way you can use the first two digits:
const unsigned char foobar[] =
{
0x22,
'A', 'B',
0x42,
33,
};
or the full string "AB"
#include <stdio.h>
#define FOO X('A', 'B', '\0')
#define BAR 33
extern int rs232_write(const unsigned char *data, unsigned char count);
const unsigned char foobar[] =
{
0x22,
#define X(a, b, c) a, b
FOO,
#undef X
#define X(a, b, c) ((char []){a, b, c})
0x42,
BAR,
};
int main(void)
{
// rs232_write(foobar,sizeof(foobar));
printf("%s\n", FOO);
return 0;
}
Output:
AB
This should work:
#include<stdio.h>
#define FOO 'A','B'
#define BAR 33
const char foobar[] = {
0x22,
FOO,
0x42,
BAR,
'\0'
};
int main(void)
{
printf("%s\n", foobar);
return 0;
}
BTW it is very bad to init the array that way, maybe you can explain your aim better.
#include <stdio.h>
#include <stdlib.h>
#define FOO "ab"
#define BAR 33
#define STRINGIFY(x) STRINGIFY2(x)
#define STRINGIFY2(x) #x
const char foobar[] = "\x22" FOO "\x42" STRINGIFY(BAR);
int main(void)
{
printf("foobar = |%s| (%ld+1 characters)\n",
foobar, (long) sizeof(foobar) - 1);
return EXIT_SUCCESS;
}
Running this program ouputs:
foobar = |"abB33| (6+1 characters)
The problem is that the compiler doesn't know, at the time of compilation, where the string literal "AB" will be placed in memory. Its location will be decided when the program is linked or possibly when it is loaded into memory.
Therefore using it will not result in a compile-time constant that is required for the initialization of the foobar array.
In this case you really have no option but to use setting foobar[1] and foobar[2] once at run-time. However, even on an extremely small embedded system this will not incur much overhead either in memory or in time. If the program runs more than a few seconds it will most likely not even be measurable.
Hi i have below simple program
#include <stdio.h>
#include <string.h>
typedef unsigned long long uint64;
void getvalue(uint64 *getValue)
{
unsigned char arr[8] = {0xAB, 0xCD, 0x12, 0x34, 0xFF, 0xED, 0xCA, 0x01};
memcpy(getValue, arr, sizeof(uint64));
}
void main()
{
uint64 getValue;
getvalue(&getValue);
printf("value :0x%08x and sizeof(uint64) = %d", getValue, sizeof(uint64));
}
This program to copy content in 8 byte variable but when i ran it i see below output which shows only 4 bytes copied.
value :0x3412cdab and sizeof(uint64) = 8
So can anyone point out me what is the issue?
The copy is ok, You have to printf with long long unsigned
printf("0x%llx", (unsigned long long) getValue);
This program shows correctly the voltages but not specify the direction on the Hyperterminal. It keeps showing N for all the values of voltages.
I've been trying but still couldn't find the bug.
Here's my code down below.
// Using microcontroller AT89C51, ADC 0804 for display on hyperterminal
#include <reg51.h>
#include <string.h>
#define input P1
void delay(unsigned int time);
void SerTx(unsigned char x);
void SerTx_str(unsigned char msg[]);
void SerInit();
void convert(unsigned int p);
unsigned char msg[] ="Voltage= ";
sbit wint =P3^4;
void main()
{
unsigned int y,z,p;
int d1,d2,d3;
unsigned char buffer[10];
SerInit();
input=0xff;
while(1)
{
wint=0;
delay(1);
wint=1;
delay(5);
wint=0;
delay(10);
z=input;
y=z*2;
d1=y%10;
y=y/10;
d2=y%10;
d3=y/10;
buffer[0] =d3+48;
buffer[1] =d2+48;
buffer[2] =d1+48;
SerTx_str(msg);
SerTx_str(buffer);
SerTx_str(" ");
p=buffer;
convert(p);
SerTx(13);
SerTx(13);
delay(20);
SerTx(10);
}
}
p = buffer;
Now p holds the address of buffer (because buffer is an array, this is short for p = &buffer[0];)
convert(p);
Now you convert the value in p - that is, you convert the address of buffer.
I'm guessing you want to convert the same number you're displaying? The number you're displaying is z*2, so just use:
convert(z*2);
I am not receiving anything in buffer. Wherever I printf my buffer, it is always empty or shows garbage value. Can anyone help?
I defined header, packet and called them in my main, but buffer still shows garbage.
#include <stdint.h>
struct header {
uint16_t f1;
uint16_t f2;
uint32_t f3;
};
struct data {
uint16_t pf1;
uint64_t pf2;
};
#include <arpa/inet.h>
#include <string.h>
#include <stdint.h>
#include "packet.h"
void htonHeader(struct header h, char buffer[8]) {
uint16_t u16;
uint32_t u32;
u16 = htons(h.f1);
memcpy(buffer+0, &u16, 2);
printf("Value of buff is: %hu\n",buffer);
u16 = htons(h.f2);
memcpy(buffer+2, &u16, 2);
u32 = htonl(h.f3);
memcpy(buffer+4, &u32, 4);
}
void htonData(struct data d, char buffer[10]) {
uint16_t u16;
uint32_t u32;
u16 = htons(d.pf1);
memcpy(buffer+0, &u16, 2);
u32 = htonl(d.pf2>>32);
memcpy(buffer+2, &u32, 4);
u32 = htonl(d.pf2);
memcpy(buffer+6,&u32, 4);
}
void HeaderData(struct header h, struct data d, char buffer[18]) {
htonHeader(h, buffer+0);
htonData(d, buffer+8);
printf("buff is: %s\n",buffer);
}
#include <stdio.h>
#include "packet.c"
#include <string.h>
#include<stdlib.h>
int main(){
struct header h;
struct data d;
char buff[18];
//printf("Packet is: %s\n",buff);
printf("Generating Packets..... \n");
h.f1=1;
d.pf1=2;
h.f2=3;
d.pf2=4;
h.f3=5;
HeaderData(h,d,buff);
strcat(buff,buff+8);
printf("Packet is: %s\n",buff);
return 0;
}
The problem is that your printf()s are either syntactically wrong (printf( "%hu", ... ); expects an unsigned short as parameter, but you pass a pointer) or you try to print buff by using "%s" but the content is binary, not text. What you could do instead was doing some kind of hexdump, like:
int i;
for( i=0; i<sizeof( buff ); i++ ) {
printf( "%x ", buff[i] & 0xff );
}
puts( "" ); // terminate the line
Please note, that using sizeof works im main() only, in the other function you've got to determine the buffer size differently.
Besides: because of the binary content of buff, you can't use strcat(). Even if you have made sure that there is a '\0' behind the last value you have copied (I haven't checked if you have), depending on the integer values you copy, there may be another '\0' value before that one and strcat() would overwrite everything form that point on.