🚀 go-pugleaf

RetroBBS NetNews Server

Inspired by RockSolid Light RIP Retro Guy

Thread View: pl.comp.os.linux.programowanie
4 messages
4 total messages Started by Borneq Thu, 26 Nov 2015 10:41
Niskopoziomowy timer
#72770
Author: Borneq
Date: Thu, 26 Nov 2015 10:41
306 lines
9884 bytes
Chciałem użyć biblioteki XCB jako nowszej niż Xlib. Mam przykład z 
http://xcb.freedesktop.org/tutorial/fonts/ który wyświetla tylko tekst w 
oknie. Teraz chciałem podłączyć timer czy dwa, które w callbacku 
zmieniają ten tekst.
Używam timer_create(CLOCK_REALTIME, &sigev, &tid) który łączy sygnały z 
timerem.
Jednak nic się  nie dzieje.
Kompilacja: w Code::Blocks nie trzeba ustawiać ścieżek, tylko dodać 
biblioteki linkera: xcb i rt.

Oto moja próba:
--------------------------------------------------------
#include <stdlib.h>
#include <stdio.h>
#include <string.h>
#include <inttypes.h>


#include <xcb/xcb.h>
#include <signal.h>
#include <time.h>

#define WIDTH 300
#define HEIGHT 100


static xcb_gcontext_t getFontGC (xcb_connection_t *c,
                              xcb_screen_t     *screen,
                              xcb_window_t      window,
                              const char       *font_name );


static void drawText (xcb_connection_t *c,
                        xcb_screen_t     *screen,
                        xcb_window_t      window,
                        int16_t           x1,
                        int16_t           y1,
                        const char       *label );


static void
testCookie (xcb_void_cookie_t cookie,
             xcb_connection_t *connection,
             char *errMessage )
{
     xcb_generic_error_t *error = xcb_request_check (connection, cookie);
     if (error) {
         fprintf (stderr, "ERROR: %s : %"PRIu8"\n", errMessage , 
error->error_code);
         xcb_disconnect (connection);
         exit (-1);
     }
}

static void
drawText (xcb_connection_t  *connection,
            xcb_screen_t     *screen,
            xcb_window_t      window,
            int16_t           x1,
            int16_t           y1,
            const char       *label )
{

     /* get graphics context */
     xcb_gcontext_t gc = getFontGC (connection, screen, window, "fixed");


     /* draw the text */
     xcb_void_cookie_t textCookie = xcb_image_text_8_checked (connection,
                                                              strlen 
(label),
                                                              window,
                                                              gc,
                                                              x1, y1,
                                                              label );

     testCookie(textCookie, connection, "can't paste text");


     /* free the gc */
     xcb_void_cookie_t gcCookie = xcb_free_gc (connection, gc);

     testCookie(gcCookie, connection, "can't free gc");
}


static xcb_gcontext_t
getFontGC (xcb_connection_t  *connection,
            xcb_screen_t      *screen,
            xcb_window_t       window,
            const char        *font_name )
{
     /* get font */
     xcb_font_t font = xcb_generate_id (connection);
     xcb_void_cookie_t fontCookie = xcb_open_font_checked (connection,
                                                           font,
                                                           strlen 
(font_name),
                                                           font_name );

     testCookie(fontCookie, connection, "can't open font");


     /* create graphics context */
     xcb_gcontext_t  gc            = xcb_generate_id (connection);
     uint32_t        mask          = XCB_GC_FOREGROUND | 
XCB_GC_BACKGROUND | XCB_GC_FONT;
     uint32_t        value_list[3] = { screen->black_pixel,
                                       screen->white_pixel,
                                       font };

     xcb_void_cookie_t gcCookie = xcb_create_gc_checked (connection,
                                                         gc,
                                                         window,
                                                         mask,
                                                         value_list );

     testCookie(gcCookie, connection, "can't create gc");


     /* close font */
     fontCookie = xcb_close_font_checked (connection, font);

     testCookie(fontCookie, connection, "can't close font");

     return gc;
}

char *text_message = "abcdef";
#define SIGTIMER (SIGRTMAX)
#define SIG SIGUSR1

static timer_t     tid1;
static timer_t     tid2;

void SignalHandler(int signo, siginfo_t* info, void* context)
{
     if (signo == SIGTIMER) {
         text_message = "parameter frequency";

     }
     else if (signo == SIG) {
         text_message = "Communication frequency";

     }
}

timer_t SetTimer(int signo, long int sec, int mode)
{
static struct sigevent sigev;
static timer_t tid;
static struct itimerspec itval;
static struct itimerspec oitval;

// Create the POSIX timer to generate signo
sigev.sigev_notify = SIGEV_SIGNAL;
sigev.sigev_signo = signo;
sigev.sigev_value.sival_ptr = &tid;


if (timer_create(CLOCK_REALTIME, &sigev, &tid) == 0) {
     itval.it_value.tv_sec = sec;
     itval.it_value.tv_nsec = 0;

     if (mode == 1) {
         itval.it_interval.tv_sec = sec;
         itval.it_interval.tv_nsec = 0;
     }
else {
     itval.it_interval.tv_sec = sec;
         itval.it_interval.tv_nsec = 0;
     }

     if (timer_settime(tid, 0, &itval, &oitval) != 0) {
         perror("time_settime error!");
     }
}
else {
     perror("timer_create error!");
     return NULL;
}
return tid;
}

int main ()
{
     /* get the connection */
     int screenNum;
     xcb_connection_t *connection = xcb_connect (NULL, &screenNum);
     if (!connection) {
         fprintf (stderr, "ERROR: can't connect to an X server\n");
         return -1;
     }


     /* get the current screen */
     xcb_screen_iterator_t iter = xcb_setup_roots_iterator 
(xcb_get_setup (connection));

     // we want the screen at index screenNum of the iterator
     for (int i = 0; i < screenNum; ++i) {
         xcb_screen_next (&iter);
     }

     xcb_screen_t *screen = iter.data;

     if (!screen) {
         fprintf (stderr, "ERROR: can't get the current screen\n");
         xcb_disconnect (connection);
         return -1;
     }


     /* create the window */
     xcb_window_t window = xcb_generate_id (connection);

     uint32_t mask = XCB_CW_BACK_PIXEL | XCB_CW_EVENT_MASK;
     uint32_t values[2];
     values[0] = screen->white_pixel;
     values[1] = XCB_EVENT_MASK_KEY_RELEASE |
                 XCB_EVENT_MASK_BUTTON_PRESS |
                 XCB_EVENT_MASK_EXPOSURE |
                 XCB_EVENT_MASK_POINTER_MOTION;

     xcb_void_cookie_t windowCookie = xcb_create_window_checked (connection,
 
screen->root_depth,
                                                                 window, 
screen->root,
                                                                 20, 200,
                                                                 WIDTH, 
HEIGHT,
                                                                 0, 
XCB_WINDOW_CLASS_INPUT_OUTPUT,
 
screen->root_visual,
                                                                 mask, 
values);

     testCookie(windowCookie, connection, "can't create window");

     xcb_void_cookie_t mapCookie = xcb_map_window_checked (connection, 
window);

     testCookie(mapCookie, connection, "can't map window");

     xcb_flush(connection);  // make sure window is drawn



     /* event loop */
     xcb_generic_event_t  *event;
                             /* event loop */
   int done = 0;


     struct sigaction sigact;
     sigemptyset(&sigact.sa_mask);
     sigact.sa_flags = SA_SIGINFO;
     sigact.sa_sigaction = SignalHandler;
     // set up sigaction to catch signal
     if (sigaction(SIGTIMER, &sigact, NULL) == -1)
     {
         perror("sigaction failed");
         exit( EXIT_FAILURE );
     }

     int  param_delay = 2;
     tid1=SetTimer(SIGTIMER, param_delay, 1);

     struct sigaction sa;
     sigemptyset(&sa.sa_mask);
     sa.sa_flags = SA_SIGINFO;
     sa.sa_sigaction = SignalHandler;
     // set up sigaction to catch signal
     if (sigaction(SIG, &sa, NULL) == -1)
     {
         perror("sa failed");
         exit( EXIT_FAILURE );
     }

int commn_delay = 1;
     tid2=SetTimer(SIG, commn_delay, 1);


   while (!done && (event = xcb_wait_for_event(connection))) {
     switch (event->response_type & ~0x80) {
     case XCB_EXPOSE:    /* draw or redraw the window */
       drawText (connection,
                               screen,
                               window,
                               10, HEIGHT - 10,
                               text_message );
       xcb_flush(connection);
       break;
     case XCB_KEY_RELEASE:  /* exit on key press */
       done = 1;
       break;
     }
     free(event);
   }
                         /* close connection to server */
   xcb_disconnect(connection);

   return 0;
}
Re: Niskopoziomowy timer
#72771
Author: Borneq
Date: Thu, 26 Nov 2015 11:06
8 lines
1192 bytes
W dniu 2015-11-26 o 11:41, Borneq pisze:
> Używam timer_create(CLOCK_REALTIME, &sigev, &tid) który łączy sygnały z
> timerem.
> Jednak nic się  nie dzieje.

Nawet konsolowy przykład z man
http://man7.org/linux/man-pages/man2/timer_create.2.html
nie za dobrze działa - sleep na 1 sekundę i co z tego? handler nie wołany.
Re: Niskopoziomowy timer
#72772
Author: Borneq
Date: Thu, 26 Nov 2015 11:10
8 lines
1261 bytes
W dniu 2015-11-26 o 12:06, Borneq pisze:
> Nawet konsolowy przykład z man
> http://man7.org/linux/man-pages/man2/timer_create.2.html
> nie za dobrze działa - sleep na 1 sekundę i co z tego? handler nie wołany.

http://stackoverflow.com/questions/5740954/problem-in-timers-and-signal
Już zaczyna łapać
tylko teraz nie konsolowy a pętla eventów
Re: Niskopoziomowy timer
#72773
Author: Borneq
Date: Thu, 26 Nov 2015 16:38
5 lines
1191 bytes
W dniu 2015-11-26 o 12:10, Borneq pisze:
> http://stackoverflow.com/questions/5740954/problem-in-timers-and-signal
> Już zaczyna łapać
> tylko teraz nie konsolowy a pętla eventów
Udało się : https://gist.github.com/borneq/c629924b60d117ec5c31
Thread Navigation

This is a paginated view of messages in the thread with full content displayed inline.

Messages are displayed in chronological order, with the original post highlighted in green.

Use pagination controls to navigate through all messages in large threads.

Back to All Threads