So I have this code that I have to edit a bit but the code itself doesn't compile when I try in mobaxterm and since I don't really have much experience with C++ I hope u guys can help. This is the code:
//critical_example2.c
#include <sys/ipc.h>
#include <sys/sem.h>
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include "se207_sems.h"
int main(int argc, char argv[]){
//Use our source file as the "key"
int id=se207_semget("critical_example2.c",1);
int pid=fork();
if(pid){
//P1
while(1){
se207_wait(id);
printf("In critical section P1 ... \n");
rsleep();
printf("Ending critical section P1 ... \n");
se207_signal(id);
}
}else{
//P2
while(1){
se207_wait(id);
printf("In critical section P2 ... \n");
rsleep();
printf("Ending critical section P2 ... \n");
se207_signal(id);
}
}
}
This are the errors i get:
toneve#hvs-its-lnx01:~$ gcc critical_example2.c
In file included from critical_example2.c:9:0:
se207_sems.h: In function ‘se207_wait’:
se207_sems.h:91:6: warning: type of ‘id’ defaults to ‘int’ [-Wimplicit-int]
void se207_wait(id){
^
se207_sems.h: In function ‘se207_signal’:
se207_sems.h:95:6: warning: type of ‘id’ defaults to ‘int’ [-Wimplicit-int]
void se207_signal(id){
This might be the problematic code:
#include <sys/ipc.h>
#include <sys/sem.h>
#include <stdio.h>
#include <stdlib.h>
void rsleep(){
//Random sleep function. Comes in handy demoing stuff.
int stime=2+(rand()/(float)(RAND_MAX))*4;
printf("Sleeping for %d secs\n",stime);
sleep(stime);
}
int se207_semget(char* path, int val){
//Very simple semaphore "getting",
//always uses 1 as the project ID
//takes path to file and initial value of semaphore
int id; /* Number by which the semaphore
is known within a program */
union semun {
int val;
struct semid_ds *buf;
ushort * array;
} argument;
argument.val = val;
/* Create the semaphore with external key from
ftok if it doesn't already
exist. Give permissions to the world. */
id = semget(ftok(path,1), 1, 0666 | IPC_CREAT);
/* Always check system returns. */
if(id < 0)
{
fprintf(stderr, "Unable to obtain semaphore.\n");
exit(0);
}
/* Set the value of the number 0 semaphore in semaphore array # id
to the value "val". */
if( semctl(id, 0, SETVAL, argument) < 0)
fprintf( stderr, "Cannot set semaphore value.\n");
else
fprintf(stderr, "Semaphore %d initialized with path '%s'.\n",
ftok(path,1),path);
return id;
}
void se207_semop(int id,int val){
struct sembuf operations[1];
int retval; /* Return value from semop() */
//simple wait on semaphore
operations[0].sem_num = 0;
/* Which operation? Subtract 1 from semaphore value to wait, add to
signal */
operations[0].sem_op = val;
operations[0].sem_flg = 0;
retval = semop(id, operations, 1);
}
int void se207_wait(id){
se207_semop(id,-1);
}
int void se207_signal(id){
se207_semop(id,1);
}
Remove the int from your se207_wait and se207_signal functions, and declare id as an int in the parameter list.
void se207_wait(int id){
se207_semop(id,-1);
}
void se207_signal(int id){
se207_semop(id,1);
}
Related
Need some help with PTHREADS. I want to keep over 1000 threads opened at any time, something like a thread pool. Here is the code :
/*
gcc -o test2 test2.cpp -static -lpthread -lstdc++
*/
#include <iostream>
#include <cstdlib>
#include <pthread.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <cstring>
#include <stdexcept>
#include <cstdlib>
int NUM_THREADS = 2000;
int MAX_THREADS = 100;
int THREADSTACK = 65536;
struct thread_struct{
int arg1;
int arg2;
};
pthread_mutex_t mutex_;
static unsigned int thread_count = 0;
string exec(const char* cmd)
{
int DEBUG=0;
char buffer[5000];
string result = "";
FILE* pipe = popen(cmd, "r");
if (!pipe && DEBUG) throw runtime_error("popen() failed!");
try
{
while (!feof(pipe))
{
if (fgets(buffer, 128, pipe) != NULL)
{
result += buffer;
}
}
}
catch(...)
{
pclose(pipe);
throw;
}
pclose(pipe);
return result;
}
void *thread_test(void *arguments)
{
pthread_mutex_lock(&mutex_);
thread_count++;
pthread_mutex_unlock(&mutex_);
// long tid;
// tid = (long)threadid;
struct thread_struct *args = (thread_struct*)arguments;
/*
printf("ARG1=%d\n",args->arg1);
printf("ARG2=%d\n",args->arg2);
*/
int thread_id = (int) args->arg1;
/*
int random_sleep;
random_sleep = rand() % 10 + 1;
printf ("RAND=[%d]\n", random_sleep);
sleep(random_sleep);
*/
int random_sleep;
random_sleep = rand() % 10 + 5;
// printf ("RAND=[%d]\n", random_sleep);
char command[100];
memset(command,0,sizeof(command));
sprintf(command,"sleep %d",random_sleep);
exec(command);
random_sleep = rand() % 100000 + 500000;
usleep(random_sleep);
// simulation of a work between 5 and 10 seconds
// sleep(random_sleep);
// printf("#%d -> sleep=%d total_threads=%u\n",thread_id,random_sleep,thread_count);
pthread_mutex_lock(&mutex_);
thread_count--;
pthread_mutex_unlock(&mutex_);
pthread_exit(NULL);
}
int main()
{
// pthread_t threads[NUM_THREADS];
int rc;
int i;
usleep(10000);
srand ((unsigned)time(NULL));
unsigned int thread_count_now = 0;
pthread_attr_t attrs;
pthread_attr_init(&attrs);
pthread_attr_setstacksize(&attrs, THREADSTACK);
pthread_mutex_init(&mutex_, NULL);
for( i=0; i < NUM_THREADS; i++ )
{
create_thread:
pthread_mutex_lock(&mutex_);
thread_count_now = thread_count;
pthread_mutex_unlock(&mutex_);
// printf("thread_count in for = [%d]\n",thread_count_now);
if(thread_count_now < MAX_THREADS)
{
printf("CREATE thread [%d]\n",i);
struct thread_struct struct1;
struct1.arg1 = i;
struct1.arg2 = 999;
pthread_t temp_thread;
rc = pthread_create(&temp_thread, NULL, &thread_test, (void *)&struct1);
if (rc)
{
printf("Unable to create thread %d\n",rc);
sleep(1);
pthread_detach(temp_thread);
goto create_thread;
}
}
else
{
printf("Thread POOL full %d of %d\n",thread_count_now,MAX_THREADS);
sleep(1);
goto create_thread;
}
}
pthread_attr_destroy(&attrs);
pthread_mutex_destroy(&mutex_);
// pthread_attr_destroy(&attrs);
printf("Proccess completed!\n");
pthread_exit(NULL);
return 1;
}
After spawning 300 threads it begins to give
errors, return code from pthread_create() is 11, and after that keeps executing them one by one.
What im i doing wrong?
According to this website, error code 11 corresponds to EAGAIN which means according to this:
Insufficient resources to create another thread.
A system-imposed limit on the number of threads was encountered.
Hence to solve your problem either create less threads or wait for running ones to finish before creating new ones.
You can also change default thread stack size see pthread_attr_setstacksize
I have written two program (program 1 and program 2) to communicate with each other using shared memory. program 1 reads from a file a sentence and pass it after modification to get first letter of each word and its size to the next program ( program 2) . I faced race condition problem. I added Peterson algorithm but once I execute the 2 programs one in foreground and one in background I didn't get any result.
-once i remove the Peterson algorithm my programs work
-i'm working in linux using c++
program 1
#include<iostream>
#include<fstream>
#include <sys/ipc.h>
#include <sys/shm.h>
#include <sys/types.h>
#include <stdlib.h>
#include <unistd.h>
using namespace std;
int filesize(){
ifstream input;
input.open("file1.txt");
string temp;
int i = 0;
while(input>>temp){i++;}
input.close();
return i;
}
struct shdata
{
char c;
int n;
int size;
bool flag[2];
int turn;
};
int main(){
ifstream input;
input.open("file1.txt");
int shmid;
key_t key = 8006;
struct shdata *shm;
shmid = shmget(key, sizeof(struct shdata), IPC_CREAT | 0666);
if(shmid < 0){
cout<<"Error .. Can not get memory\n";
exit(0);
}
shm = (struct shdata *)shmat (shmid, NULL, 0);
if(shm <= (struct shdata *)(0))
{
cout<<"Errors.. Can not attach\n";
exit(1);
}
shm->flag[0]=false;
shm->flag[1]=true;
string temp;
while(input>>temp){
shm->flag[0]=true;
shm->turn = 1;
while(shm->flag[1]== true && shm-> turn == 1 );
shm->c=temp[0];
shm->n=temp.size();
shm->size = filesize();
shm->flag[0]=false;
sleep(1);
}
return 0;
}
program 2
#include<iostream>
#include<fstream>
#include <sys/ipc.h>
#include <sys/shm.h>
#include <sys/types.h>
#include <stdlib.h>
#include <unistd.h>
using namespace std;
int filesize(){
ifstream input;
input.open("file1.txt");
string temp;
int i = 0;
while(input>>temp){i++;}
input.close();
return i;
}
struct shdata
{
char c;
int n;
int size;
bool flag[2];
int turn;
};
int main(){
int shmid;
key_t key = 8006;
struct shdata *shm;
shmid = shmget(key, sizeof(struct shdata), 0);
if(shmid < 0)
{
cout<<"Error .. Can not get memory\n";
exit(0);
}
shm = (struct shdata *)shmat (shmid,0, 0);
if(shm <= (struct shdata *)(0))
{
cout<<"Error .. Can not attach\n";
exit(1);
}
int c =0;
while(c<shm->size){
shm->flag[1] = true;
shm->turn=0;
while( shm->flag[0]==false && shm->turn == 0);
sleep(1);
for(int i = 0; i < shm->n ;i++)
{
cout<<shm->c;
}
cout<<endl;
shm->flag[1]=false;
c++;
}
shmctl(shmid, IPC_RMID, NULL);
return 0;
}
program 2 never gets into the while(c<shm->size) loop because at that point shm->size is 0. To get around it, progran 1 should initialize shm->size before program 2 reaches that point. This might lead to another race condition because there doesn't seem to be any mechanism to ensure that the shared memory is initialized by program 1 before program 2 starts using it.
It seems to work without the Peterson algorithm because in that case program 1 doesn't wait on the flag and initializes shm->size further down in the loop.
You are using the flag member to synchronize you 2 programs but this cant work because you cant suppose the sequence of read/writes. You must use a small dialect in order to make your two programs starts in the correct order.
I am doing a program to open, write and read the port ttyUSB0, I have the next program and I don´t write anything. Can anyone help me please????
My question is that I have a problem with the write or read function, because I can´t read and write in the ttyUSB0 port, and I search a solution to write and read ttyUSB0 port.
#include <sys/time.h>
#include <fcntl.h>
#include <unistd.h>
#include <string.h>
#include <termios.h>
#include <iostream>
#include <sys/types.h>
#include <sys/stat.h>
using namespace std;
int serial_open(char *serial_name, speed_t baud)
{
struct termios newtermios;
int fd;
fd = open(serial_name,O_RDWR | O_NOCTTY);
newtermios.c_cflag= CBAUD | CS8 | CLOCAL | CREAD;
newtermios.c_iflag=IGNPAR;
newtermios.c_oflag=0;
newtermios.c_lflag=0;
newtermios.c_cc[VMIN]=1;
newtermios.c_cc[VTIME]=0;
cfsetospeed(&newtermios,baud);
cfsetispeed(&newtermios,baud);
if (tcflush(fd,TCIFLUSH)==-1) return -1;
if (tcflush(fd,TCOFLUSH)==-1) return -1;
if (tcsetattr(fd,TCSANOW,&newtermios)==-1) return -1;
return fd;
}
void serial_send(int serial_fd, char *data, int size)
{
write(serial_fd, data, size);
}
int serial_read(int serial_fd, char *data, int size, int timeout_usec)
{
fd_set fds;
struct timeval timeout;
int count=0;
int ret;
int n;
do {
FD_ZERO(&fds);
FD_SET (serial_fd, &fds);
timeout.tv_sec = 0;
timeout.tv_usec = timeout_usec;
ret=select (FD_SETSIZE,&fds, NULL, NULL,&timeout);
if (ret==1) {
n=read (serial_fd, &data[count], size-count);
count+=n;
data[count]=0;
}
} while (count<size && ret==1);
return count;
}
void serial_close(int fd)
{
close(fd);
}
int main(int argc, char *argv[])
{
int serial_fd, n, longitud,;
char *device=”at”;
char *data;
longitud=strlen(device);
serial_fd = serial_open("/dev/ttyUSB0",B38400);
if (serial_fd == -1) {
printf ("Error opening the serial device: %s\n",argv[1]);
perror("OPEN");
exit(0);
}
printf("SERIAL OPEN:%s\n", device);
serial_send(serial_fd, device, longitud);
printf ("String sent------> %s\n",device);
n=serial_read(serial_fd,data,longitud,10000);
printf("Se ha recibido %s \n Tamaño: %d\n n:%d \n serial_fd:%d\n",data, longitud,n,serial_fd);
puts(data);
serial_close(serial_fd);
// cout << "Hello world!" << endl;
return 0;
}
Your program works just fine with the writing and reading, but you have another problem: Undefined behavior.
You have a pointer variable in your main function named data, and you pass this to your serial_read function. But nowhere do you make this pointer actually point anywhere, so when that pointer is dereferenced you have the undefined behavior.
Local (non-static) variables are not initialized, their value is indeterminate. You need to initialize the variable, to make it actually point somewhere. I recommend you make it into an array instead.
And then when you call serial_read you only ask to read two bytes (the length of the string "at"), instead of the actual size of the data (which currently is none), you need to pass the actual size of the buffer instead.
So to sum it up:
int main(void)
{
...
char data[256];
...
n = serial_read(serial_fd, data, sizeof(data), 10000);
...
}
I'm trying to create 12 new instances of a class and run each of them it's a own thread, but they seam to share the same data.
all 12 instances are on the same X and Y position, but they each should move on a random direction.
as you can see in the code, i tried various apraoches and i can't find out why.
what am i doing wrong here?
p.s. yes ... i know there are still some unused variables.
p.s.s i have looked at many places and also here before i posted the question
enemy.cpp
#include "enemy.h"
#include <time.h>
#include <windows.h>
FILE* pEnemyFile = fopen ("enemylog.txt","w");
Enemy::Enemy(const MouseServer& mServer, int& lastMousePosX, int& lastMousePosY, int& winSizeX, int& winSizeY )
:mouseServer(mServer),
lastMouseX( ( lastMousePosX ) ? lastMousePosX : 0 ), // evaluate if we get the reference
lastMouseY( ( lastMousePosY ) ? lastMousePosY : 0 ),
myPositionX(0),
myPositionY(0),
winSizeX(winSizeX),
winSizeY(winSizeY),
x(0),
y(0)
{
// original source:
// http://msdn.microsoft.com/en-us/library/windows/desktop/ms682516(v=vs.85).aspx
// Allocate memory for thread data.
EDATA threadEnemyData = (EDATA) HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY,sizeof(enemyData));
// http://www.codeproject.com/Articles/14746/Multithreading-Tutorial
// http://www.codeguru.com/cpp/w-d/dislog/win32/article.php/c9823/Win32-Thread-Synchronization-Part-I-Overview.htm
// usefull information
// http://msdn.microsoft.com/en-us/library/z3x8b09y(v=vs.100).aspx
if( threadEnemyData == NULL )
{
//If the array allocation fails, the system is out of memory
//so there is no point in trying to print an error message.
//Just terminate execution.
ExitProcess(2);
}
threadEnemyData->X = 0;
threadEnemyData->Y = 0;
this->hThread = CreateThread(
NULL,
0,
this->MyThreadFunction,
this,
/*threadEnemyData,*/
0,
&this->dwThreadID
);
// Check the return value for success.
// If CreateThread fails, terminate execution.
// This will automatically clean up threads and memory.
if (this->hThread== NULL)
{
ErrorHandler(TEXT("CreateThread"));
ExitProcess(3);
}
//End of main thread creation loop.
}
Enemy::~Enemy()
{
// Wait until all threads have terminated.
WaitForSingleObject(this->hThread,INFINITE);
// Close all thread handles and free memory allocations.
this->hDefaultProcessHeap = GetProcessHeap();
if (this->hDefaultProcessHeap == NULL) {
}
CloseHandle(this->hThread);
//if(threadEnemyData != NULL)
//{
// HeapFree(GetProcessHeap(), 0, threadEnemyData);
// hThread = NULL; // Ensure address is not reused.
//}
// close debug file
fclose (pEnemyFile);
}
void Enemy::Draw(D3DGraphics& gfx)
{
gfx.PutPixel(this->x + 0,this->y,255,255,255);
gfx.PutPixel(this->x + 1,this->y,255,255,255);
gfx.PutPixel(this->x + 2,this->y,255,255,255);
gfx.PutPixel(this->x + 3,this->y,255,255,255);
gfx.PutPixel(this->x + 4,this->y,255,255,255);
gfx.PutPixel(this->x + 5,this->y,255,255,255);
gfx.PutPixel(this->x + 6,this->y,255,255,255);
gfx.PutPixel(this->x + 7,this->y,255,255,255);
}
// read
// http://www.tek-tips.com/viewthread.cfm?qid=1068278
DWORD WINAPI Enemy::MyThreadFunction( void* param )
{
Enemy* self = (Enemy*) param;
////self-> // <-- "this"
return self->NewThread();
}
/* initialize random seed: */
// the itelligence loop of your enemy/object
DWORD Enemy::NewThread()
{
do
{
srand ( time(NULL) );
/* generate random number: */
//self->x += rand() % 4;
//self->y += rand() % 4;
this->x += rand() % 4;
this->y += rand() % 4;
// debug stuff
char buffer[ 64 ];
sprintf_s(buffer, "enemy: x: %d Y: %d id: %d\n", (char)this->x, (char)this->y, (char)this->dwThreadID);
fputs (buffer,pEnemyFile);
// allow processor time to other threads
Sleep(100);
}while(true); // endles loop
}
void Enemy::ErrorHandler(LPTSTR lpszFunction)
{
// Retrieve the system error message for the last-error code.
this->dw = GetLastError();
// todo
}
enemy.h
#pragma once
#include "timer.h"
#include "D3DGraphics.h"
#include "D3DGraphics.h"
#include "Mouse.h"
/////// thread stuf
#include <tchar.h>
#include <strsafe.h>
#include <stdio.h>
#include <stdlib.h>
#include <time.h>
class Enemy
{
public:
Enemy();
Enemy(const MouseServer& mServer, int& lastMousePos, int& lastMousePosY, int& winSizeX, int& winSizeY);
~Enemy();
static DWORD WINAPI MyThreadFunction( LPVOID lpParam );
DWORD Enemy::NewThread();
void ErrorHandler(LPTSTR lpszFunction);
void lookingForFood();
void Draw(D3DGraphics& gfx);
int Enemy::correctX(int xParam);
int Enemy::correctY(int yParam);
private:
int myPositionX;
int myPositionY;
int lastMouseX;
int lastMouseY;
int winSizeX;
int winSizeY;
//int moveToX; // todo
//int moveToY;
int x;
int y;
// threading stuff
typedef struct ENEMYDATA // don't forget "typedef "
{
int X;
int Y; // test
} enemyData, *EDATA;
// Cast the parameter to the correct data type.
// The pointer is known to be valid because
// it was checked for NULL before the thread was created.
static Enemy* self;
HANDLE hThread;
DWORD dwThreadID;
HANDLE hDefaultProcessHeap;
DWORD dw; // error message
EDATA* threadEnemyData;
MouseClient mouseServer;
//D3DGraphics& grafix;
Timer timer;
};
It's commented out in your thread proc, but looks like you were on the right track:
srand ( time(NULL) );
It didn't work for you because all the threads start so fast that they end up with time(NULL) returning the same value for each thread. This means they're all using the same random sequence. Try seeding rand with the thread ID (or some other source that's unique per thread) and you should see unique pseudorandom number sequences.
I've written a program that uses a vector and a map.
When i run it, i get this following error message:
lru: malloc.c:3552: munmap_chunk: Assertion `ret == 0' failed.
Abort
What is the meaning of this error message?
P.S.
When i run my program with valgrind - it passes, with no 'abort'.
Here's my code:
#include <stdio.h>
#include <stdlib.h>
#include <iostream>
#include <vector>
#include <map>
#include "byutr.h"
using namespace std;
///////////////////////////////////////////
/* DEFINE ZONE */
///////////////////////////////////////////
#define NUM_OF_ARGS 4
#define NUM_OF_DIFF_PAGES 100000
///////////////////////////////////////////
/* GLOBAL VARIABLES */
///////////////////////////////////////////
p2AddrTr tr;//a pre-defined struct
vector<uint32_t> stack;
vector<int> depths;
map<uint32_t, int> pages;
map<uint32_t, int>::iterator it;
int main(int argc, char **argv)
{
stack.reserve(NUM_OF_DIFF_PAGES);
FILE *ifp;//TODO remove!
// unsigned long i;//TODO int OR unsigned long??
int i;
unsigned long pCnt =0;
if(argc != NUM_OF_ARGS)
{
fprintf(stderr,"usage: lru <pageSize> <startAt> <numAccesses>\n");
exit(1);
}
int pageSize = atoi(argv[1]);
int startAt = atoi(argv[2]);
int numAccesses = atoi(argv[3]);
int k;
//Skip some entries if needed
for(k=0;k< startAt;k++){
fread(&tr, sizeof(p2AddrTr), 1, stdin);
}
//size_t bytes = fread(&tr, sizeof(p2AddrTr),1, stdin);
//fread(&tr, sizeof(p2AddrTr),1, stdin); TODO here??
i = 0;
while((!feof(stdin)) && (i<numAccesses)){
fread(&tr, sizeof(p2AddrTr),1, stdin);
//prints the address of the memory access
printf("%08lx ", tr.addr);
cout<<endl;
int currAddr = (tr.addr)/pageSize;
if(pages.find(currAddr) == pages.end()){//New page
pCnt++;
//insert the new page to the map
pages.insert(pair<uint32_t, int>(currAddr,pCnt));
//insert the new page to the 'stack'
stack.push_back(currAddr);
}
else{//page already exists
size_t j;
//find the page in the stack
for(j=0;j<stack.size();j++){
if(stack[j] == currAddr){
cout << "passed stack[j]"<<endl;
depths.push_back(stack.size() - j);
break;
}
}
//move the page to the top of the stack
stack.erase(stack.begin() + (j-1));
stack.push_back(currAddr);
}
i++;
}
return (0);
}
I see at least one error:
stack.erase(stack.begin() + (j-1));
If j is 0, this tries to erase an element before the beginning of the list, resulting in a crash.