Changeset 387416b in mainline for uspace


Ignore:
Timestamp:
2009-12-12T10:11:35Z (16 years ago)
Author:
Pavel Rimsky <pavel@…>
Branches:
lfn, master, serial, ticket/834-toolchain-update, topic/msim-upgrade, topic/simplify-dev-export
Children:
99de22b
Parents:
58d5803d (diff), 1e4cada (diff)
Note: this is a merge changeset, the changes displayed below correspond to the merge itself.
Use the (diff) links above to see all the changes relative to each parent.
Message:

Synchronizing with head.

Location:
uspace
Files:
9 added
52 edited
2 moved

Legend:

Unmodified
Added
Removed
  • uspace/Makefile

    r58d5803d r387416b  
    4848        srv/devmap \
    4949        srv/part/mbr_part \
     50        srv/clip \
    5051        app/edit \
    5152        app/tetris \
  • uspace/app/bdsh/input.c

    r58d5803d r387416b  
    3636#include <io/keycode.h>
    3737#include <io/style.h>
     38#include <io/color.h>
    3839#include <vfs/vfs.h>
     40#include <clipboard.h>
     41#include <macros.h>
    3942#include <errno.h>
     43#include <assert.h>
    4044#include <bool.h>
    4145
     
    4751#include "exec.h"
    4852
    49 static void read_line(char *, int);
     53#define HISTORY_LEN 10
     54
     55/** Text input field. */
     56typedef struct {
     57        /** Buffer holding text currently being edited */
     58        wchar_t buffer[INPUT_MAX + 1];
     59        /** Screen coordinates of the top-left corner of the text field */
     60        int col0, row0;
     61        /** Screen dimensions */
     62        int con_cols, con_rows;
     63        /** Number of characters in @c buffer */
     64        int nc;
     65        /** Caret position within buffer */
     66        int pos;
     67        /** Selection mark position within buffer */
     68        int sel_start;
     69
     70        /** History (dynamically allocated strings) */
     71        char *history[1 + HISTORY_LEN];
     72        /** Number of entries in @c history, not counting [0] */
     73        int hnum;
     74        /** Current position in history */
     75        int hpos;
     76        /** Exit flag */
     77        bool done;
     78} tinput_t;
     79
     80/** Seek direction */
     81typedef enum {
     82        seek_backward = -1,
     83        seek_forward = 1
     84} seek_dir_t;
     85
     86static tinput_t tinput;
     87
     88static char *tinput_read(tinput_t *ti);
     89static void tinput_insert_string(tinput_t *ti, const char *str);
     90static void tinput_sel_get_bounds(tinput_t *ti, int *sa, int *sb);
     91static bool tinput_sel_active(tinput_t *ti);
     92static void tinput_sel_all(tinput_t *ti);
     93static void tinput_sel_delete(tinput_t *ti);
     94static void tinput_key_ctrl(tinput_t *ti, console_event_t *ev);
     95static void tinput_key_shift(tinput_t *ti, console_event_t *ev);
     96static void tinput_key_ctrl_shift(tinput_t *ti, console_event_t *ev);
     97static void tinput_key_unmod(tinput_t *ti, console_event_t *ev);
     98static void tinput_pre_seek(tinput_t *ti, bool shift_held);
     99static void tinput_post_seek(tinput_t *ti, bool shift_held);
    50100
    51101/* Tokenizes input from console, sees if the first word is a built-in, if so
     
    99149}
    100150
    101 static void read_line(char *buffer, int n)
     151static void tinput_display_tail(tinput_t *ti, int start, int pad)
     152{
     153        static wchar_t dbuf[INPUT_MAX + 1];
     154        int sa, sb;
     155        int i, p;
     156
     157        tinput_sel_get_bounds(ti, &sa, &sb);
     158
     159        console_goto(fphone(stdout), (ti->col0 + start) % ti->con_cols,
     160            ti->row0 + (ti->col0 + start) / ti->con_cols);
     161        console_set_color(fphone(stdout), COLOR_BLACK, COLOR_WHITE, 0);
     162
     163        p = start;
     164        if (p < sa) {
     165                memcpy(dbuf, ti->buffer + p, (sa - p) * sizeof(wchar_t));
     166                dbuf[sa - p] = '\0';
     167                printf("%ls", dbuf);
     168                p = sa;
     169        }
     170
     171        if (p < sb) {
     172                fflush(stdout);
     173                console_set_color(fphone(stdout), COLOR_BLACK, COLOR_RED, 0);
     174                memcpy(dbuf, ti->buffer + p,
     175                    (sb - p) * sizeof(wchar_t));
     176                dbuf[sb - p] = '\0';
     177                printf("%ls", dbuf);
     178                p = sb;
     179        }
     180
     181        fflush(stdout);
     182        console_set_color(fphone(stdout), COLOR_BLACK, COLOR_WHITE, 0);
     183
     184        if (p < ti->nc) {
     185                memcpy(dbuf, ti->buffer + p,
     186                    (ti->nc - p) * sizeof(wchar_t));
     187                dbuf[ti->nc - p] = '\0';
     188                printf("%ls", dbuf);
     189        }
     190
     191        for (i = 0; i < pad; ++i)
     192                putchar(' ');
     193        fflush(stdout);
     194}
     195
     196static char *tinput_get_str(tinput_t *ti)
     197{
     198        return wstr_to_astr(ti->buffer);
     199}
     200
     201static void tinput_position_caret(tinput_t *ti)
     202{
     203        console_goto(fphone(stdout), (ti->col0 + ti->pos) % ti->con_cols,
     204            ti->row0 + (ti->col0 + ti->pos) / ti->con_cols);
     205}
     206
     207/** Update row0 in case the screen could have scrolled. */
     208static void tinput_update_origin(tinput_t *ti)
     209{
     210        int width, rows;
     211
     212        width = ti->col0 + ti->nc;
     213        rows = (width / ti->con_cols) + 1;
     214
     215        /* Update row0 if the screen scrolled. */
     216        if (ti->row0 + rows > ti->con_rows)
     217                ti->row0 = ti->con_rows - rows;
     218}
     219
     220static void tinput_insert_char(tinput_t *ti, wchar_t c)
     221{
     222        int i;
     223        int new_width, new_height;
     224
     225        if (ti->nc == INPUT_MAX)
     226                return;
     227
     228        new_width = ti->col0 + ti->nc + 1;
     229        if (new_width % ti->con_cols == 0) {
     230                /* Advancing to new line. */
     231                new_height = (new_width / ti->con_cols) + 1;
     232                if (new_height >= ti->con_rows)
     233                        return; /* Disallow text longer than 1 page for now. */
     234        }
     235
     236        for (i = ti->nc; i > ti->pos; --i)
     237                ti->buffer[i] = ti->buffer[i - 1];
     238
     239        ti->buffer[ti->pos] = c;
     240        ti->pos += 1;
     241        ti->nc += 1;
     242        ti->buffer[ti->nc] = '\0';
     243        ti->sel_start = ti->pos;
     244
     245        tinput_display_tail(ti, ti->pos - 1, 0);
     246        tinput_update_origin(ti);
     247        tinput_position_caret(ti);
     248}
     249
     250static void tinput_insert_string(tinput_t *ti, const char *str)
     251{
     252        int i;
     253        int new_width, new_height;
     254        int ilen;
     255        wchar_t c;
     256        size_t off;
     257
     258        ilen = min((ssize_t) str_length(str), INPUT_MAX - ti->nc);
     259        if (ilen == 0)
     260                return;
     261
     262        new_width = ti->col0 + ti->nc + ilen;
     263        new_height = (new_width / ti->con_cols) + 1;
     264        if (new_height >= ti->con_rows)
     265                return; /* Disallow text longer than 1 page for now. */
     266
     267        for (i = ti->nc - 1; i >= ti->pos; --i)
     268                ti->buffer[i + ilen] = ti->buffer[i];
     269
     270        off = 0; i = 0;
     271        while (i < ilen) {
     272                c = str_decode(str, &off, STR_NO_LIMIT);
     273                if (c == '\0')
     274                        break;
     275
     276                /* Filter out non-printable chars. */
     277                if (c < 32)
     278                        c = 32;
     279
     280                ti->buffer[ti->pos + i] = c;
     281                ++i;
     282        }
     283
     284        ti->pos += ilen;
     285        ti->nc += ilen;
     286        ti->buffer[ti->nc] = '\0';
     287        ti->sel_start = ti->pos;
     288
     289        tinput_display_tail(ti, ti->pos - ilen, 0);
     290        tinput_update_origin(ti);
     291        tinput_position_caret(ti);
     292}
     293
     294static void tinput_backspace(tinput_t *ti)
     295{
     296        int i;
     297
     298        if (tinput_sel_active(ti)) {
     299                tinput_sel_delete(ti);
     300                return;
     301        }
     302
     303        if (ti->pos == 0)
     304                return;
     305
     306        for (i = ti->pos; i < ti->nc; ++i)
     307                ti->buffer[i - 1] = ti->buffer[i];
     308        ti->pos -= 1;
     309        ti->nc -= 1;
     310        ti->buffer[ti->nc] = '\0';
     311        ti->sel_start = ti->pos;
     312
     313        tinput_display_tail(ti, ti->pos, 1);
     314        tinput_position_caret(ti);
     315}
     316
     317static void tinput_delete(tinput_t *ti)
     318{
     319        if (tinput_sel_active(ti)) {
     320                tinput_sel_delete(ti);
     321                return;
     322        }
     323
     324        if (ti->pos == ti->nc)
     325                return;
     326
     327        ti->pos += 1;
     328        ti->sel_start = ti->pos;
     329
     330        tinput_backspace(ti);
     331}
     332
     333static void tinput_seek_cell(tinput_t *ti, seek_dir_t dir, bool shift_held)
     334{
     335        tinput_pre_seek(ti, shift_held);
     336
     337        if (dir == seek_forward) {
     338                if (ti->pos < ti->nc)
     339                        ti->pos += 1;
     340        } else {
     341                if (ti->pos > 0)
     342                        ti->pos -= 1;
     343        }
     344
     345        tinput_post_seek(ti, shift_held);
     346}
     347
     348static void tinput_seek_word(tinput_t *ti, seek_dir_t dir, bool shift_held)
     349{
     350        tinput_pre_seek(ti, shift_held);
     351
     352        if (dir == seek_forward) {
     353                if (ti->pos == ti->nc)
     354                        return;
     355
     356                while (1) {
     357                        ti->pos += 1;
     358
     359                        if (ti->pos == ti->nc)
     360                                break;
     361
     362                        if (ti->buffer[ti->pos - 1] == ' ' &&
     363                            ti->buffer[ti->pos] != ' ')
     364                                break;
     365                }
     366        } else {
     367                if (ti->pos == 0)
     368                        return;
     369
     370                while (1) {
     371                        ti->pos -= 1;
     372
     373                        if (ti->pos == 0)
     374                                break;
     375
     376                        if (ti->buffer[ti->pos - 1] == ' ' &&
     377                            ti->buffer[ti->pos] != ' ')
     378                                break;
     379                }
     380
     381        }
     382
     383        tinput_post_seek(ti, shift_held);
     384}
     385
     386static void tinput_seek_vertical(tinput_t *ti, seek_dir_t dir, bool shift_held)
     387{
     388        tinput_pre_seek(ti, shift_held);
     389
     390        if (dir == seek_forward) {
     391                if (ti->pos + ti->con_cols <= ti->nc)
     392                        ti->pos = ti->pos + ti->con_cols;
     393        } else {
     394                if (ti->pos - ti->con_cols >= 0)
     395                        ti->pos = ti->pos - ti->con_cols;
     396        }
     397
     398        tinput_post_seek(ti, shift_held);
     399}
     400
     401static void tinput_seek_max(tinput_t *ti, seek_dir_t dir, bool shift_held)
     402{
     403        tinput_pre_seek(ti, shift_held);
     404
     405        if (dir == seek_backward)
     406                ti->pos = 0;
     407        else
     408                ti->pos = ti->nc;
     409
     410        tinput_post_seek(ti, shift_held);
     411}
     412
     413static void tinput_pre_seek(tinput_t *ti, bool shift_held)
     414{
     415        if (tinput_sel_active(ti) && !shift_held) {
     416                /* Unselect and redraw. */
     417                ti->sel_start = ti->pos;
     418                tinput_display_tail(ti, 0, 0);
     419                tinput_position_caret(ti);
     420        }
     421}
     422
     423static void tinput_post_seek(tinput_t *ti, bool shift_held)
     424{
     425        if (shift_held) {
     426                /* Selecting text. Need redraw. */
     427                tinput_display_tail(ti, 0, 0);
     428        } else {
     429                /* Shift not held. Keep selection empty. */
     430                ti->sel_start = ti->pos;
     431        }
     432        tinput_position_caret(ti);
     433}
     434
     435static void tinput_history_insert(tinput_t *ti, char *str)
     436{
     437        int i;
     438
     439        if (ti->hnum < HISTORY_LEN) {
     440                ti->hnum += 1;
     441        } else {
     442                if (ti->history[HISTORY_LEN] != NULL)
     443                        free(ti->history[HISTORY_LEN]);
     444        }
     445
     446        for (i = ti->hnum; i > 1; --i)
     447                ti->history[i] = ti->history[i - 1];
     448
     449        ti->history[1] = str_dup(str);
     450
     451        if (ti->history[0] != NULL) {
     452                free(ti->history[0]);
     453                ti->history[0] = NULL;
     454        }
     455}
     456
     457static void tinput_set_str(tinput_t *ti, char *str)
     458{
     459        str_to_wstr(ti->buffer, INPUT_MAX, str);
     460        ti->nc = wstr_length(ti->buffer);
     461        ti->pos = ti->nc;
     462        ti->sel_start = ti->pos;
     463}
     464
     465static void tinput_sel_get_bounds(tinput_t *ti, int *sa, int *sb)
     466{
     467        if (ti->sel_start < ti->pos) {
     468                *sa = ti->sel_start;
     469                *sb = ti->pos;
     470        } else {
     471                *sa = ti->pos;
     472                *sb = ti->sel_start;
     473        }
     474}
     475
     476static bool tinput_sel_active(tinput_t *ti)
     477{
     478        return ti->sel_start != ti->pos;
     479}
     480
     481static void tinput_sel_all(tinput_t *ti)
     482{
     483        ti->sel_start = 0;
     484        ti->pos = ti->nc;
     485        tinput_display_tail(ti, 0, 0);
     486        tinput_position_caret(ti);
     487}
     488
     489static void tinput_sel_delete(tinput_t *ti)
     490{
     491        int sa, sb;
     492
     493        tinput_sel_get_bounds(ti, &sa, &sb);
     494        if (sa == sb)
     495                return;
     496
     497        memmove(ti->buffer + sa, ti->buffer + sb,
     498            (ti->nc - sb) * sizeof(wchar_t));
     499        ti->pos = ti->sel_start = sa;
     500        ti->nc -= (sb - sa);
     501        ti->buffer[ti->nc] = '\0';
     502
     503        tinput_display_tail(ti, sa, sb - sa);
     504        tinput_position_caret(ti);
     505}
     506
     507static void tinput_sel_copy_to_cb(tinput_t *ti)
     508{
     509        int sa, sb;
     510        wchar_t tmp_c;
     511        char *str;
     512
     513        tinput_sel_get_bounds(ti, &sa, &sb);
     514
     515        if (sb < ti->nc) {
     516                tmp_c = ti->buffer[sb];
     517                ti->buffer[sb] = '\0';
     518        }
     519
     520        str = wstr_to_astr(ti->buffer + sa);
     521
     522        if (sb < ti->nc)
     523                ti->buffer[sb] = tmp_c;
     524
     525        if (str == NULL)
     526                goto error;
     527
     528        if (clipboard_put_str(str) != EOK)
     529                goto error;
     530
     531        free(str);
     532        return;
     533error:
     534        return;
     535        /* TODO: Give the user some warning. */
     536}
     537
     538static void tinput_paste_from_cb(tinput_t *ti)
     539{
     540        char *str;
     541        int rc;
     542
     543        rc = clipboard_get_str(&str);
     544        if (rc != EOK || str == NULL)
     545                return; /* TODO: Give the user some warning. */
     546
     547        tinput_insert_string(ti, str);
     548        free(str);
     549}
     550
     551static void tinput_history_seek(tinput_t *ti, int offs)
     552{
     553        int pad;
     554
     555        if (ti->hpos + offs < 0 || ti->hpos + offs > ti->hnum)
     556                return;
     557
     558        if (ti->history[ti->hpos] != NULL) {
     559                free(ti->history[ti->hpos]);
     560                ti->history[ti->hpos] = NULL;
     561        }
     562
     563        ti->history[ti->hpos] = tinput_get_str(ti);
     564        ti->hpos += offs;
     565
     566        pad = ti->nc - str_length(ti->history[ti->hpos]);
     567        if (pad < 0) pad = 0;
     568
     569        tinput_set_str(ti, ti->history[ti->hpos]);
     570        tinput_display_tail(ti, 0, pad);
     571        tinput_update_origin(ti);
     572        tinput_position_caret(ti);
     573}
     574
     575/** Initialize text input field.
     576 *
     577 * Must be called before using the field. It clears the history.
     578 */
     579static void tinput_init(tinput_t *ti)
     580{
     581        ti->hnum = 0;
     582        ti->hpos = 0;
     583        ti->history[0] = NULL;
     584}
     585
     586/** Read in one line of input. */
     587static char *tinput_read(tinput_t *ti)
    102588{
    103589        console_event_t ev;
    104         size_t offs, otmp;
    105         wchar_t dec;
    106 
    107         offs = 0;
    108         while (true) {
     590        char *str;
     591
     592        fflush(stdout);
     593
     594        if (console_get_size(fphone(stdin), &ti->con_cols, &ti->con_rows) != EOK)
     595                return NULL;
     596        if (console_get_pos(fphone(stdin), &ti->col0, &ti->row0) != EOK)
     597                return NULL;
     598
     599        ti->pos = ti->sel_start = 0;
     600        ti->nc = 0;
     601        ti->buffer[0] = '\0';
     602        ti->done = false;
     603
     604        while (!ti->done) {
    109605                fflush(stdout);
    110606                if (!console_get_event(fphone(stdin), &ev))
    111                         return;
    112                
     607                        return NULL;
     608
    113609                if (ev.type != KEY_PRESS)
    114610                        continue;
    115                
    116                 if (ev.key == KC_ENTER || ev.key == KC_NENTER)
    117                         break;
    118                 if (ev.key == KC_BACKSPACE) {
    119                         if (offs > 0) {
    120                                 /*
    121                                  * Back up until we reach valid start of
    122                                  * character.
    123                                  */
    124                                 while (offs > 0) {
    125                                         --offs; otmp = offs;
    126                                         dec = str_decode(buffer, &otmp, n);
    127                                         if (dec != U_SPECIAL)
    128                                                 break;
    129                                 }
    130                                 putchar('\b');
    131                         }
    132                         continue;
     611
     612                if ((ev.mods & KM_CTRL) != 0 &&
     613                    (ev.mods & (KM_ALT | KM_SHIFT)) == 0) {
     614                        tinput_key_ctrl(ti, &ev);
    133615                }
     616
     617                if ((ev.mods & KM_SHIFT) != 0 &&
     618                    (ev.mods & (KM_CTRL | KM_ALT)) == 0) {
     619                        tinput_key_shift(ti, &ev);
     620                }
     621
     622                if ((ev.mods & KM_CTRL) != 0 &&
     623                    (ev.mods & KM_SHIFT) != 0 &&
     624                    (ev.mods & KM_ALT) == 0) {
     625                        tinput_key_ctrl_shift(ti, &ev);
     626                }
     627
     628                if ((ev.mods & (KM_CTRL | KM_ALT | KM_SHIFT)) == 0) {
     629                        tinput_key_unmod(ti, &ev);
     630                }
     631
    134632                if (ev.c >= ' ') {
    135                         if (chr_encode(ev.c, buffer, &offs, n - 1) == EOK)
    136                                 putchar(ev.c);
     633                        tinput_sel_delete(ti);
     634                        tinput_insert_char(ti, ev.c);
    137635                }
    138636        }
     637
     638        ti->pos = ti->nc;
     639        tinput_position_caret(ti);
    139640        putchar('\n');
    140         buffer[offs] = '\0';
    141 }
    142 
    143 /* TODO:
    144  * Implement something like editline() / readline(), if even
    145  * just for command history and making arrows work. */
     641
     642        str = tinput_get_str(ti);
     643        if (str_cmp(str, "") != 0)
     644                tinput_history_insert(ti, str);
     645
     646        ti->hpos = 0;
     647
     648        return str;
     649}
     650
     651static void tinput_key_ctrl(tinput_t *ti, console_event_t *ev)
     652{
     653        switch (ev->key) {
     654        case KC_LEFT:
     655                tinput_seek_word(ti, seek_backward, false);
     656                break;
     657        case KC_RIGHT:
     658                tinput_seek_word(ti, seek_forward, false);
     659                break;
     660        case KC_UP:
     661                tinput_seek_vertical(ti, seek_backward, false);
     662                break;
     663        case KC_DOWN:
     664                tinput_seek_vertical(ti, seek_forward, false);
     665                break;
     666        case KC_X:
     667                tinput_sel_copy_to_cb(ti);
     668                tinput_sel_delete(ti);
     669                break;
     670        case KC_C:
     671                tinput_sel_copy_to_cb(ti);
     672                break;
     673        case KC_V:
     674                tinput_sel_delete(ti);
     675                tinput_paste_from_cb(ti);
     676                break;
     677        case KC_A:
     678                tinput_sel_all(ti);
     679                break;
     680        default:
     681                break;
     682        }
     683}
     684
     685static void tinput_key_ctrl_shift(tinput_t *ti, console_event_t *ev)
     686{
     687        switch (ev->key) {
     688        case KC_LEFT:
     689                tinput_seek_word(ti, seek_backward, true);
     690                break;
     691        case KC_RIGHT:
     692                tinput_seek_word(ti, seek_forward, true);
     693                break;
     694        case KC_UP:
     695                tinput_seek_vertical(ti, seek_backward, true);
     696                break;
     697        case KC_DOWN:
     698                tinput_seek_vertical(ti, seek_forward, true);
     699                break;
     700        default:
     701                break;
     702        }
     703}
     704
     705static void tinput_key_shift(tinput_t *ti, console_event_t *ev)
     706{
     707        switch (ev->key) {
     708        case KC_LEFT:
     709                tinput_seek_cell(ti, seek_backward, true);
     710                break;
     711        case KC_RIGHT:
     712                tinput_seek_cell(ti, seek_forward, true);
     713                break;
     714        case KC_UP:
     715                tinput_seek_vertical(ti, seek_backward, true);
     716                break;
     717        case KC_DOWN:
     718                tinput_seek_vertical(ti, seek_forward, true);
     719                break;
     720        case KC_HOME:
     721                tinput_seek_max(ti, seek_backward, true);
     722                break;
     723        case KC_END:
     724                tinput_seek_max(ti, seek_forward, true);
     725                break;
     726        default:
     727                break;
     728        }
     729}
     730
     731static void tinput_key_unmod(tinput_t *ti, console_event_t *ev)
     732{
     733        switch (ev->key) {
     734        case KC_ENTER:
     735        case KC_NENTER:
     736                ti->done = true;
     737                break;
     738        case KC_BACKSPACE:
     739                tinput_backspace(ti);
     740                break;
     741        case KC_DELETE:
     742                tinput_delete(ti);
     743                break;
     744        case KC_LEFT:
     745                tinput_seek_cell(ti, seek_backward, false);
     746                break;
     747        case KC_RIGHT:
     748                tinput_seek_cell(ti, seek_forward, false);
     749                break;
     750        case KC_HOME:
     751                tinput_seek_max(ti, seek_backward, false);
     752                break;
     753        case KC_END:
     754                tinput_seek_max(ti, seek_forward, false);
     755                break;
     756        case KC_UP:
     757                tinput_history_seek(ti, +1);
     758                break;
     759        case KC_DOWN:
     760                tinput_history_seek(ti, -1);
     761                break;
     762        default:
     763                break;
     764        }
     765}
     766
    146767void get_input(cliuser_t *usr)
    147768{
    148         char line[INPUT_MAX];
     769        char *str;
    149770
    150771        fflush(stdout);
     
    154775        console_set_style(fphone(stdout), STYLE_NORMAL);
    155776
    156         read_line(line, INPUT_MAX);
    157         /* Make sure we don't have rubbish or a C/R happy user */
    158         if (str_cmp(line, "") == 0 || str_cmp(line, "\n") == 0)
    159                 return;
    160         usr->line = str_dup(line);
    161 
     777        str = tinput_read(&tinput);
     778
     779        /* Check for empty input. */
     780        if (str_cmp(str, "") == 0) {
     781                free(str);
     782                return;
     783        }
     784
     785        usr->line = str;
    162786        return;
    163787}
    164788
     789void input_init(void)
     790{
     791        tinput_init(&tinput);
     792}
  • uspace/app/bdsh/input.h

    r58d5803d r387416b  
    88extern void get_input(cliuser_t *);
    99extern int tok_input(cliuser_t *);
     10extern void input_init(void);
    1011
    1112#endif
  • uspace/app/bdsh/scli.c

    r58d5803d r387416b  
    6464        usr->prompt = (char *) NULL;
    6565        usr->lasterr = 0;
     66
     67        input_init();
     68
    6669        return (int) cli_set_prompt(usr);
    6770}
  • uspace/app/edit/edit.c

    r58d5803d r387416b  
    3636
    3737#include <stdio.h>
     38#include <stdlib.h>
    3839#include <sys/types.h>
    3940#include <vfs/vfs.h>
     
    4445#include <align.h>
    4546#include <macros.h>
     47#include <clipboard.h>
    4648#include <bool.h>
    4749
     
    7375        tag_t caret_pos;
    7476
     77        /** Start of selection */
     78        tag_t sel_start;
     79
    7580        /**
    7681         * Ideal column where the caret should try to get. This is used
     
    101106#define ED_INFTY 65536
    102107
     108/** Maximum filename length that can be entered. */
     109#define INFNAME_MAX_LEN 128
     110
    103111static void key_handle_unmod(console_event_t const *ev);
    104112static void key_handle_ctrl(console_event_t const *ev);
     113static void key_handle_shift(console_event_t const *ev);
     114static void key_handle_movement(unsigned int key, bool shift);
     115
    105116static int file_save(char const *fname);
     117static void file_save_as(void);
    106118static int file_insert(char *fname);
    107119static int file_save_range(char const *fname, spt_t const *spos,
    108120    spt_t const *epos);
     121static char *filename_prompt(char const *prompt, char const *init_value);
     122static char *range_get_str(spt_t const *spos, spt_t const *epos);
     123
    109124static void pane_text_display(void);
    110125static void pane_row_display(void);
     
    112127static void pane_status_display(void);
    113128static void pane_caret_display(void);
     129
    114130static void insert_char(wchar_t c);
    115131static void delete_char_before(void);
     
    117133static void caret_update(void);
    118134static void caret_move(int drow, int dcolumn, enum dir_spec align_dir);
     135
     136static bool selection_active(void);
     137static void selection_sel_all(void);
     138static void selection_get_points(spt_t *pa, spt_t *pb);
     139static void selection_delete(void);
     140static void selection_copy(void);
     141static void insert_clipboard_data(void);
     142
    119143static void pt_get_sof(spt_t *pt);
    120144static void pt_get_eof(spt_t *pt);
     145static int tag_cmp(tag_t const *a, tag_t const *b);
     146static int spt_cmp(spt_t const *a, spt_t const *b);
     147static int coord_cmp(coord_t const *a, coord_t const *b);
     148
    121149static void status_display(char const *str);
    122150
     
    150178
    151179        if (argc == 2) {
    152                 doc.file_name = argv[1];
     180                doc.file_name = str_dup(argv[1]);
    153181        } else if (argc > 1) {
    154182                printf("Invalid arguments.\n");
    155183                return -2;
    156184        } else {
    157                 doc.file_name = "/edit.txt";
     185                doc.file_name = NULL;
    158186        }
    159187
    160188        new_file = false;
    161189
    162         if (file_insert(doc.file_name) != EOK)
     190        if (doc.file_name == NULL || file_insert(doc.file_name) != EOK)
    163191                new_file = true;
    164192
    165193        /* Move to beginning of file. */
    166194        caret_move(-ED_INFTY, -ED_INFTY, dir_before);
     195
     196        /* Place selection start tag. */
     197        tag_get_pt(&pane.caret_pos, &pt);
     198        sheet_place_tag(&doc.sh, &pt, &pane.sel_start);
    167199
    168200        /* Initial display */
     
    170202        pane_text_display();
    171203        pane_status_display();
    172         if (new_file)
    173                 status_display("File not found. Created empty file.");
     204        if (new_file && doc.file_name != NULL)
     205                status_display("File not found. Starting empty file.");
    174206        pane_caret_display();
    175207
     
    184216                        /* Handle key press. */
    185217                        if (((ev.mods & KM_ALT) == 0) &&
     218                            ((ev.mods & KM_SHIFT) == 0) &&
    186219                             (ev.mods & KM_CTRL) != 0) {
    187220                                key_handle_ctrl(&ev);
    188                         } else if ((ev.mods & (KM_CTRL | KM_ALT)) == 0) {
     221                        } else if (((ev.mods & KM_ALT) == 0) &&
     222                            ((ev.mods & KM_CTRL) == 0) &&
     223                             (ev.mods & KM_SHIFT) != 0) {
     224                                key_handle_shift(&ev);
     225                        } else if ((ev.mods & (KM_CTRL | KM_ALT | KM_SHIFT)) == 0) {
    189226                                key_handle_unmod(&ev);
    190227                        }
     
    201238                if (pane.rflags & REDRAW_CARET)
    202239                        pane_caret_display();
    203                        
    204240        }
    205241
     
    214250        switch (ev->key) {
    215251        case KC_ENTER:
     252                selection_delete();
    216253                insert_char('\n');
    217254                caret_update();
    218255                break;
    219256        case KC_LEFT:
    220                 caret_move(0, -1, dir_before);
    221                 break;
    222257        case KC_RIGHT:
    223                 caret_move(0, 0, dir_after);
    224                 break;
    225258        case KC_UP:
    226                 caret_move(-1, 0, dir_before);
    227                 break;
    228259        case KC_DOWN:
    229                 caret_move(+1, 0, dir_before);
    230                 break;
    231260        case KC_HOME:
    232                 caret_move(0, -ED_INFTY, dir_before);
    233                 break;
    234261        case KC_END:
    235                 caret_move(0, +ED_INFTY, dir_before);
    236                 break;
    237262        case KC_PAGE_UP:
    238                 caret_move(-pane.rows, 0, dir_before);
    239                 break;
    240263        case KC_PAGE_DOWN:
    241                 caret_move(+pane.rows, 0, dir_before);
     264                key_handle_movement(ev->key, false);
    242265                break;
    243266        case KC_BACKSPACE:
    244                 delete_char_before();
     267                if (selection_active())
     268                        selection_delete();
     269                else
     270                        delete_char_before();
    245271                caret_update();
    246272                break;
    247273        case KC_DELETE:
    248                 delete_char_after();
     274                if (selection_active())
     275                        selection_delete();
     276                else
     277                        delete_char_after();
    249278                caret_update();
    250279                break;
    251280        default:
    252281                if (ev->c >= 32 || ev->c == '\t') {
     282                        selection_delete();
    253283                        insert_char(ev->c);
    254284                        caret_update();
     
    258288}
    259289
     290/** Handle Shift-key combination. */
     291static void key_handle_shift(console_event_t const *ev)
     292{
     293        switch (ev->key) {
     294        case KC_LEFT:
     295        case KC_RIGHT:
     296        case KC_UP:
     297        case KC_DOWN:
     298        case KC_HOME:
     299        case KC_END:
     300        case KC_PAGE_UP:
     301        case KC_PAGE_DOWN:
     302                key_handle_movement(ev->key, true);
     303                break;
     304        default:
     305                if (ev->c >= 32 || ev->c == '\t') {
     306                        selection_delete();
     307                        insert_char(ev->c);
     308                        caret_update();
     309                }
     310                break;
     311        }
     312}
     313
    260314/** Handle Ctrl-key combination. */
    261315static void key_handle_ctrl(console_event_t const *ev)
     
    266320                break;
    267321        case KC_S:
    268                 (void) file_save(doc.file_name);
     322                if (doc.file_name != NULL)
     323                        file_save(doc.file_name);
     324                else
     325                        file_save_as();
     326                break;
     327        case KC_E:
     328                file_save_as();
     329                break;
     330        case KC_C:
     331                selection_copy();
     332                break;
     333        case KC_V:
     334                selection_delete();
     335                insert_clipboard_data();
     336                pane.rflags |= REDRAW_TEXT;
     337                caret_update();
     338                break;
     339        case KC_X:
     340                selection_copy();
     341                selection_delete();
     342                pane.rflags |= REDRAW_TEXT;
     343                caret_update();
     344                break;
     345        case KC_A:
     346                selection_sel_all();
    269347                break;
    270348        default:
     
    273351}
    274352
     353static void key_handle_movement(unsigned int key, bool select)
     354{
     355        spt_t pt;
     356        spt_t caret_pt;
     357        coord_t c_old, c_new;
     358        bool had_sel;
     359
     360        /* Check if we had selection before. */
     361        tag_get_pt(&pane.caret_pos, &caret_pt);
     362        tag_get_pt(&pane.sel_start, &pt);
     363        had_sel = !spt_equal(&caret_pt, &pt);
     364
     365        switch (key) {
     366        case KC_LEFT:
     367                caret_move(0, -1, dir_before);
     368                break;
     369        case KC_RIGHT:
     370                caret_move(0, 0, dir_after);
     371                break;
     372        case KC_UP:
     373                caret_move(-1, 0, dir_before);
     374                break;
     375        case KC_DOWN:
     376                caret_move(+1, 0, dir_before);
     377                break;
     378        case KC_HOME:
     379                caret_move(0, -ED_INFTY, dir_before);
     380                break;
     381        case KC_END:
     382                caret_move(0, +ED_INFTY, dir_before);
     383                break;
     384        case KC_PAGE_UP:
     385                caret_move(-pane.rows, 0, dir_before);
     386                break;
     387        case KC_PAGE_DOWN:
     388                caret_move(+pane.rows, 0, dir_before);
     389                break;
     390        default:
     391                break;
     392        }
     393
     394        if (select == false) {
     395                /* Move sel_start to the same point as caret. */
     396                sheet_remove_tag(&doc.sh, &pane.sel_start);
     397                tag_get_pt(&pane.caret_pos, &pt);
     398                sheet_place_tag(&doc.sh, &pt, &pane.sel_start);
     399        }
     400
     401        if (select) {
     402                tag_get_pt(&pane.caret_pos, &pt);
     403                spt_get_coord(&caret_pt, &c_old);
     404                spt_get_coord(&pt, &c_new);
     405
     406                if (c_old.row == c_new.row)
     407                        pane.rflags |= REDRAW_ROW;
     408                else
     409                        pane.rflags |= REDRAW_TEXT;
     410
     411        } else if (had_sel == true) {
     412                /* Redraw because text was unselected. */
     413                pane.rflags |= REDRAW_TEXT;
     414        }
     415}
    275416
    276417/** Save the document. */
     
    285426
    286427        rc = file_save_range(fname, &sp, &ep);
    287         status_display("File saved.");
     428
     429        switch (rc) {
     430        case EINVAL:
     431                status_display("Error opening file!");
     432                break;
     433        case EIO:
     434                status_display("Error writing data!");
     435                break;
     436        default:
     437                status_display("File saved.");
     438                break;
     439        }
    288440
    289441        return rc;
     442}
     443
     444/** Change document name and save. */
     445static void file_save_as(void)
     446{
     447        char *old_fname, *fname;
     448        int rc;
     449
     450        old_fname = (doc.file_name != NULL) ? doc.file_name : "";
     451        fname = filename_prompt("Save As", old_fname);
     452        if (fname == NULL) {
     453                status_display("Save cancelled.");
     454                return;
     455        }
     456
     457        rc = file_save(fname);
     458        if (rc != EOK)
     459                return;
     460
     461        if (doc.file_name != NULL)
     462                free(doc.file_name);
     463        doc.file_name = fname;
     464}
     465
     466/** Ask for a file name. */
     467static char *filename_prompt(char const *prompt, char const *init_value)
     468{
     469        console_event_t ev;
     470        char *str;
     471        wchar_t buffer[INFNAME_MAX_LEN + 1];
     472        int max_len;
     473        int nc;
     474        bool done;
     475
     476        asprintf(&str, "%s: %s", prompt, init_value);
     477        status_display(str);
     478        console_goto(con, 1 + str_length(str), scr_rows - 1);
     479        free(str);
     480
     481        console_set_color(con, COLOR_WHITE, COLOR_BLACK, 0);
     482
     483        max_len = min(INFNAME_MAX_LEN, scr_columns - 4 - str_length(prompt));
     484        str_to_wstr(buffer, max_len + 1, init_value);
     485        nc = wstr_length(buffer);
     486        done = false;
     487
     488        while (!done) {
     489                console_get_event(con, &ev);
     490
     491                if (ev.type == KEY_PRESS) {
     492                        /* Handle key press. */
     493                        if (((ev.mods & KM_ALT) == 0) &&
     494                             (ev.mods & KM_CTRL) != 0) {
     495                                ;
     496                        } else if ((ev.mods & (KM_CTRL | KM_ALT)) == 0) {
     497                                switch (ev.key) {
     498                                case KC_ESCAPE:
     499                                        return NULL;
     500                                case KC_BACKSPACE:
     501                                        if (nc > 0) {
     502                                                putchar('\b');
     503                                                fflush(stdout);
     504                                                --nc;
     505                                        }
     506                                        break;
     507                                case KC_ENTER:
     508                                        done = true;
     509                                        break;
     510                                default:
     511                                        if (ev.c >= 32 && nc < max_len) {
     512                                                putchar(ev.c);
     513                                                fflush(stdout);
     514                                                buffer[nc++] = ev.c;
     515                                        }
     516                                        break;
     517                                }
     518                        }
     519                }
     520        }
     521
     522        buffer[nc] = '\0';
     523        str = wstr_to_astr(buffer);
     524
     525        console_set_color(con, COLOR_BLACK, COLOR_WHITE, 0);
     526
     527        return str;
    290528}
    291529
     
    359597        } while (!spt_equal(&bep, epos));
    360598
    361         fclose(f);
     599        if (fclose(f) != EOK)
     600                return EIO;
    362601
    363602        return EOK;
     603}
     604
     605/** Return contents of range as a new string. */
     606static char *range_get_str(spt_t const *spos, spt_t const *epos)
     607{
     608        char *buf;
     609        spt_t sp, bep;
     610        size_t bytes;
     611        size_t buf_size, bpos;
     612
     613        buf_size = 1;
     614
     615        buf = malloc(buf_size);
     616        if (buf == NULL)
     617                return NULL;
     618
     619        bpos = 0;
     620        sp = *spos;
     621
     622        while (true) {
     623                sheet_copy_out(&doc.sh, &sp, epos, &buf[bpos], buf_size - bpos,
     624                    &bep);
     625                bytes = str_size(&buf[bpos]);
     626                bpos += bytes;
     627                sp = bep;
     628
     629                if (spt_equal(&bep, epos))
     630                        break;
     631
     632                buf_size *= 2;
     633                buf = realloc(buf, buf_size);
     634                if (buf == NULL)
     635                        return NULL;
     636        }
     637
     638        return buf;
    364639}
    365640
     
    408683{
    409684        int i, j, fill;
    410         spt_t rb, re, dep;
     685        spt_t rb, re, dep, pt;
    411686        coord_t rbc, rec;
    412687        char row_buf[ROW_BUF_SIZE];
     
    414689        size_t pos, size;
    415690        unsigned s_column;
     691        coord_t csel_start, csel_end, ctmp;
     692
     693        /* Determine selection start and end. */
     694
     695        tag_get_pt(&pane.sel_start, &pt);
     696        spt_get_coord(&pt, &csel_start);
     697
     698        tag_get_pt(&pane.caret_pos, &pt);
     699        spt_get_coord(&pt, &csel_end);
     700
     701        if (coord_cmp(&csel_start, &csel_end) > 0) {
     702                ctmp = csel_start;
     703                csel_start = csel_end;
     704                csel_end = ctmp;
     705        }
    416706
    417707        /* Draw rows from the sheet. */
     
    434724                /* Display text from the buffer. */
    435725
     726                if (coord_cmp(&csel_start, &rbc) <= 0 &&
     727                    coord_cmp(&rbc, &csel_end) < 0) {
     728                        fflush(stdout);
     729                        console_set_color(con, COLOR_BLACK, COLOR_RED, 0);
     730                        fflush(stdout);
     731                }
     732
    436733                console_goto(con, 0, i);
    437734                size = str_size(row_buf);
    438735                pos = 0;
    439                 s_column = 1;
     736                s_column = pane.sh_column;
    440737                while (pos < size) {
     738                        if (csel_start.row == rbc.row && csel_start.column == s_column) {
     739                                fflush(stdout);
     740                                console_set_color(con, COLOR_BLACK, COLOR_RED, 0);
     741                                fflush(stdout);
     742                        }
     743       
     744                        if (csel_end.row == rbc.row && csel_end.column == s_column) {
     745                                fflush(stdout);
     746                                console_set_color(con, COLOR_BLACK, COLOR_WHITE, 0);
     747                                fflush(stdout);
     748                        }
     749       
    441750                        c = str_decode(row_buf, &pos, size);
    442751                        if (c != '\t') {
     
    453762                }
    454763
     764                if (csel_end.row == rbc.row && csel_end.column == s_column) {
     765                        fflush(stdout);
     766                        console_set_color(con, COLOR_BLACK, COLOR_WHITE, 0);
     767                        fflush(stdout);
     768                }
     769
    455770                /* Fill until the end of display area. */
    456771
     
    463778                        putchar(' ');
    464779                fflush(stdout);
     780                console_set_color(con, COLOR_BLACK, COLOR_WHITE, 0);
    465781        }
    466782
     
    473789        spt_t caret_pt;
    474790        coord_t coord;
     791        char *fname;
    475792        int n;
    476793
     
    478795        spt_get_coord(&caret_pt, &coord);
    479796
     797        fname = (doc.file_name != NULL) ? doc.file_name : "<unnamed>";
     798
    480799        console_goto(con, 0, scr_rows - 1);
    481800        console_set_color(con, COLOR_WHITE, COLOR_BLACK, 0);
    482         n = printf(" %d, %d: File '%s'. Ctrl-S Save  Ctrl-Q Quit",
    483             coord.row, coord.column, doc.file_name);
     801        n = printf(" %d, %d: File '%s'. Ctrl-Q Quit  Ctrl-S Save  "
     802            "Ctrl-E Save As", coord.row, coord.column, fname);
    484803        printf("%*s", scr_columns - 1 - n, "");
    485804        fflush(stdout);
     
    648967}
    649968
     969/** Check for non-empty selection. */
     970static bool selection_active(void)
     971{
     972        return (tag_cmp(&pane.caret_pos, &pane.sel_start) != 0);
     973}
     974
     975static void selection_get_points(spt_t *pa, spt_t *pb)
     976{
     977        spt_t pt;
     978
     979        tag_get_pt(&pane.sel_start, pa);
     980        tag_get_pt(&pane.caret_pos, pb);
     981
     982        if (spt_cmp(pa, pb) > 0) {
     983                pt = *pa;
     984                *pa = *pb;
     985                *pb = pt;
     986        }
     987}
     988
     989/** Delete selected text. */
     990static void selection_delete(void)
     991{
     992        spt_t pa, pb;
     993        coord_t ca, cb;
     994        int rel;
     995
     996        tag_get_pt(&pane.sel_start, &pa);
     997        tag_get_pt(&pane.caret_pos, &pb);
     998        spt_get_coord(&pa, &ca);
     999        spt_get_coord(&pb, &cb);
     1000        rel = coord_cmp(&ca, &cb);
     1001
     1002        if (rel == 0)
     1003                return;
     1004
     1005        if (rel < 0)
     1006                sheet_delete(&doc.sh, &pa, &pb);
     1007        else
     1008                sheet_delete(&doc.sh, &pb, &pa);
     1009
     1010        if (ca.row == cb.row)
     1011                pane.rflags |= REDRAW_ROW;
     1012        else
     1013                pane.rflags |= REDRAW_TEXT;
     1014}
     1015
     1016static void selection_sel_all(void)
     1017{
     1018        spt_t spt, ept;
     1019
     1020        pt_get_sof(&spt);
     1021        pt_get_eof(&ept);
     1022        sheet_remove_tag(&doc.sh, &pane.sel_start);
     1023        sheet_place_tag(&doc.sh, &spt, &pane.sel_start);
     1024        sheet_remove_tag(&doc.sh, &pane.caret_pos);
     1025        sheet_place_tag(&doc.sh, &ept, &pane.caret_pos);
     1026
     1027        pane.rflags |= REDRAW_TEXT;
     1028        caret_update();
     1029}
     1030
     1031static void selection_copy(void)
     1032{
     1033        spt_t pa, pb;
     1034        char *str;
     1035
     1036        selection_get_points(&pa, &pb);
     1037        str = range_get_str(&pa, &pb);
     1038        if (str == NULL || clipboard_put_str(str) != EOK) {
     1039                status_display("Copying to clipboard failed!");
     1040        }
     1041        free(str);
     1042}
     1043
     1044static void insert_clipboard_data(void)
     1045{
     1046        char *str;
     1047        size_t off;
     1048        wchar_t c;
     1049        int rc;
     1050
     1051        rc = clipboard_get_str(&str);
     1052        if (rc != EOK || str == NULL)
     1053                return;
     1054
     1055        off = 0;
     1056
     1057        while (true) {
     1058                c = str_decode(str, &off, STR_NO_LIMIT);
     1059                if (c == '\0')
     1060                        break;
     1061
     1062                insert_char(c);
     1063        }
     1064
     1065        free(str);
     1066}
    6501067
    6511068/** Get start-of-file s-point. */
     
    6691086
    6701087        sheet_get_cell_pt(&doc.sh, &coord, dir_after, pt);
     1088}
     1089
     1090/** Compare tags. */
     1091static int tag_cmp(tag_t const *a, tag_t const *b)
     1092{
     1093        spt_t pa, pb;
     1094
     1095        tag_get_pt(a, &pa);
     1096        tag_get_pt(b, &pb);
     1097
     1098        return spt_cmp(&pa, &pb);
     1099}
     1100
     1101/** Compare s-points. */
     1102static int spt_cmp(spt_t const *a, spt_t const *b)
     1103{
     1104        coord_t ca, cb;
     1105
     1106        spt_get_coord(a, &ca);
     1107        spt_get_coord(b, &cb);
     1108
     1109        return coord_cmp(&ca, &cb);
     1110}
     1111
     1112/** Compare coordinats. */
     1113static int coord_cmp(coord_t const *a, coord_t const *b)
     1114{
     1115        if (a->row - b->row != 0)
     1116                return a->row - b->row;
     1117
     1118        return a->column - b->column;
    6711119}
    6721120
  • uspace/app/init/init.c

    r58d5803d r387416b  
    235235        spawn("/srv/kbd");
    236236        spawn("/srv/console");
     237        spawn("/srv/clip");
    237238        spawn("/srv/fhc");
    238239        spawn("/srv/obio");
  • uspace/app/trace/trace.c

    r58d5803d r387416b  
    4848#include <io/console.h>
    4949#include <io/keycode.h>
    50 #include <fibril_sync.h>
     50#include <fibril_synch.h>
    5151
    5252#include <libc.h>
  • uspace/lib/libblock/libblock.c

    r58d5803d r387416b  
    4747#include <as.h>
    4848#include <assert.h>
    49 #include <fibril_sync.h>
     49#include <fibril_synch.h>
    5050#include <adt/list.h>
    5151#include <adt/hash_table.h>
  • uspace/lib/libblock/libblock.h

    r58d5803d r387416b  
    3636
    3737#ifndef LIBBLOCK_LIBBLOCK_H_
    38 #define LIBBLOCK_LIBBLOCK_H_
     38#define LIBBLOCK_LIBBLOCK_H_
    3939
    4040#include <stdint.h>
    4141#include "../../srv/vfs/vfs.h"
    42 #include <fibril_sync.h>
     42#include <fibril_synch.h>
    4343#include <adt/hash_table.h>
    4444#include <adt/list.h>
  • uspace/lib/libc/Makefile.build

    r58d5803d r387416b  
    5050        generic/as.c \
    5151        generic/cap.c \
     52        generic/clipboard.c \
    5253        generic/devmap.c \
    5354        generic/event.c \
     
    5657        generic/string.c \
    5758        generic/fibril.c \
    58         generic/fibril_sync.c \
     59        generic/fibril_synch.c \
    5960        generic/pcb.c \
    6061        generic/smc.c \
  • uspace/lib/libc/arch/amd64/include/atomic.h

    r58d5803d r387416b  
    3737#ifndef LIBC_amd64_ATOMIC_H_
    3838#define LIBC_amd64_ATOMIC_H_
     39
     40#define LIBC_ARCH_ATOMIC_H_
     41
     42#include <atomicdflt.h>
    3943
    4044static inline void atomic_inc(atomic_t *val) {
  • uspace/lib/libc/arch/arm32/include/atomic.h

    r58d5803d r387416b  
    3737#define LIBC_arm32_ATOMIC_H_
    3838
     39#define LIBC_ARCH_ATOMIC_H_
     40#define CAS
     41
     42#include <atomicdflt.h>
     43#include <bool.h>
     44#include <sys/types.h>
     45
     46extern uintptr_t *ras_page;
     47
     48static inline bool cas(atomic_t *val, long ov, long nv)
     49{
     50        long ret = 0;
     51
     52        /*
     53         * The following instructions between labels 1 and 2 constitute a
     54         * Restartable Atomic Seqeunce. Should the sequence be non-atomic,
     55         * the kernel will restart it.
     56         */
     57        asm volatile (
     58                "1:\n"
     59                "       adr %[ret], 1b\n"
     60                "       str %[ret], %[rp0]\n"
     61                "       adr %[ret], 2f\n"
     62                "       str %[ret], %[rp1]\n"
     63                "       ldr %[ret], %[addr]\n"
     64                "       cmp %[ret], %[ov]\n"
     65                "       streq %[nv], %[addr]\n"
     66                "2:\n"
     67                "       moveq %[ret], #1\n"
     68                "       movne %[ret], #0\n"
     69                : [ret] "+&r" (ret),
     70                  [rp0] "=m" (ras_page[0]),
     71                  [rp1] "=m" (ras_page[1]),
     72                  [addr] "+m" (val->count)
     73                : [ov] "r" (ov),
     74                  [nv] "r" (nv)
     75                : "memory"
     76        );
     77
     78        ras_page[0] = 0;
     79        asm volatile ("" ::: "memory");
     80        ras_page[1] = 0xffffffff;
     81
     82        return (bool) ret;
     83}
     84
    3985/** Atomic addition.
    4086 *
     
    4692static inline long atomic_add(atomic_t *val, int i)
    4793{
    48         int ret;
    49         volatile long * mem = &(val->count);
     94        long ret = 0;
    5095
     96        /*
     97         * The following instructions between labels 1 and 2 constitute a
     98         * Restartable Atomic Seqeunce. Should the sequence be non-atomic,
     99         * the kernel will restart it.
     100         */
    51101        asm volatile (
    52         "1:\n"
    53                 "ldr r2, [%1]\n"
    54                 "add r3, r2, %2\n"
    55                 "str r3, %0\n"
    56                 "swp r3, r3, [%1]\n"
    57                 "cmp r3, r2\n"
    58                 "bne 1b\n"
     102                "1:\n"
     103                "       adr %[ret], 1b\n"
     104                "       str %[ret], %[rp0]\n"
     105                "       adr %[ret], 2f\n"
     106                "       str %[ret], %[rp1]\n"
     107                "       ldr %[ret], %[addr]\n"
     108                "       add %[ret], %[ret], %[imm]\n"
     109                "       str %[ret], %[addr]\n"
     110                "2:\n"
     111                : [ret] "+&r" (ret),
     112                  [rp0] "=m" (ras_page[0]),
     113                  [rp1] "=m" (ras_page[1]),
     114                  [addr] "+m" (val->count)
     115                : [imm] "r" (i)
     116        );
    59117
    60                 : "=m" (ret)
    61                 : "r" (mem), "r" (i)
    62                 : "r3", "r2"
    63         );
     118        ras_page[0] = 0;
     119        asm volatile ("" ::: "memory");
     120        ras_page[1] = 0xffffffff;
    64121
    65122        return ret;
  • uspace/lib/libc/arch/arm32/src/entry.s

    r58d5803d r387416b  
    3636#
    3737# r1 contains the PCB pointer
     38# r2 contains the RAS page address
    3839#
    3940__entry:
     41        # Store the RAS page address into the ras_page variable
     42        ldr r0, =ras_page
     43        str r2, [r0]
     44
    4045        # Pass pcb_ptr to __main as the first argument (in r0)
    4146        mov r0, r1
     
    4348
    4449        bl __exit
     50
     51.data
     52
     53.global ras_page
     54ras_page:
     55        .long 0
     56
  • uspace/lib/libc/arch/arm32/src/syscall.c

    r58d5803d r387416b  
    6060        register sysarg_t __arm_reg_r5 asm("r5") = p6;
    6161        register sysarg_t __arm_reg_r6 asm("r6") = id;
    62 
    63         asm volatile ( "swi"
     62       
     63        asm volatile (
     64                "swi 0"
    6465                : "=r" (__arm_reg_r0)
    6566                : "r" (__arm_reg_r0),
     
    7172                  "r" (__arm_reg_r6)
    7273        );
    73 
     74       
    7475        return __arm_reg_r0;
    7576}
  • uspace/lib/libc/arch/ia32/Makefile.inc

    r58d5803d r387416b  
    3939        arch/$(UARCH)/src/setjmp.S
    4040
     41GCC_CFLAGS += -march=pentium
    4142LFLAGS += -N
    4243
  • uspace/lib/libc/arch/ia32/include/atomic.h

    r58d5803d r387416b  
    3535#ifndef LIBC_ia32_ATOMIC_H_
    3636#define LIBC_ia32_ATOMIC_H_
     37
     38#define LIBC_ARCH_ATOMIC_H_
     39
     40#include <atomicdflt.h>
    3741
    3842static inline void atomic_inc(atomic_t *val) {
  • uspace/lib/libc/arch/ia64/include/atomic.h

    r58d5803d r387416b  
    3535#ifndef LIBC_ia64_ATOMIC_H_
    3636#define LIBC_ia64_ATOMIC_H_
     37
     38#define LIBC_ARCH_ATOMIC_H_
     39
     40#include <atomicdflt.h>
    3741
    3842static inline void atomic_inc(atomic_t *val)
  • uspace/lib/libc/arch/mips32/include/atomic.h

    r58d5803d r387416b  
    3636#ifndef LIBC_mips32_ATOMIC_H_
    3737#define LIBC_mips32_ATOMIC_H_
     38
     39#define LIBC_ARCH_ATOMIC_H_
     40
     41#include <atomicdflt.h>
    3842
    3943#define atomic_inc(x)   ((void) atomic_add(x, 1))
  • uspace/lib/libc/arch/ppc32/include/atomic.h

    r58d5803d r387416b  
    3535#ifndef LIBC_ppc32_ATOMIC_H_
    3636#define LIBC_ppc32_ATOMIC_H_
     37
     38#define LIBC_ARCH_ATOMIC_H_
     39
     40#include <atomicdflt.h>
    3741
    3842static inline void atomic_inc(atomic_t *val)
  • uspace/lib/libc/arch/sparc64/include/atomic.h

    r58d5803d r387416b  
    3636#define LIBC_sparc64_ATOMIC_H_
    3737
     38#define LIBC_ARCH_ATOMIC_H_
     39
     40#include <atomicdflt.h>
    3841#include <sys/types.h>
    3942
  • uspace/lib/libc/generic/fibril_synch.c

    r58d5803d r387416b  
    3333 */
    3434
    35 #include <fibril_sync.h>
     35#include <fibril_synch.h>
    3636#include <fibril.h>
    3737#include <async.h>
  • uspace/lib/libc/generic/futex.c

    r58d5803d r387416b  
    3636#include <atomic.h>
    3737#include <libc.h>
    38 #include <stdio.h>
    3938#include <sys/types.h>
    40 #include <kernel/synch/synch.h>
    41 
    42 /*
    43  * Note about race conditions.
    44  * Because of non-atomic nature of operations performed sequentially on the
    45  * futex counter and the futex wait queue, there is a race condition:
    46  *
    47  * (wq->missed_wakeups == 1) && (futex->count = 1)
    48  *
    49  * Scenario 1 (wait queue timeout vs. futex_up()):
    50  * 1. assume wq->missed_wakeups == 0 && futex->count == -1
    51  *    (ie. thread A sleeping, thread B in the critical section)
    52  * 2. A receives timeout and gets removed from the wait queue
    53  * 3. B wants to leave the critical section and calls futex_up()
    54  * 4. B thus changes futex->count from -1 to 0
    55  * 5. B has to call SYS_FUTEX_WAKEUP syscall to wake up the sleeping thread
    56  * 6. B finds the wait queue empty and changes wq->missed_wakeups from 0 to 1
    57  * 7. A fixes futex->count (i.e. the number of waiting threads) by changing it
    58  *    from 0 to 1
    59  *
    60  * Scenario 2 (conditional down operation vs. futex_up)
    61  * 1. assume wq->missed_wakeups == 0 && futex->count == 0
    62  *    (i.e. thread A is in the critical section)
    63  * 2. thread B performs futex_trydown() operation and changes futex->count from
    64  *    0 to -1
    65  *    B is now obliged to call SYS_FUTEX_SLEEP syscall
    66  * 3. A wants to leave the critical section and does futex_up()
    67  * 4. A thus changes futex->count from -1 to 0 and must call SYS_FUTEX_WAKEUP
    68  *    syscall
    69  * 5. B finds the wait queue empty and immediatelly aborts the conditional sleep
    70  * 6. No thread is queueing in the wait queue so wq->missed_wakeups changes from
    71  *    0 to 1
    72  * 6. B fixes futex->count (i.e. the number of waiting threads) by changing it
    73  *    from 0 to 1
    74  *
    75  * Both scenarios allow two threads to be in the critical section
    76  * simultaneously. One without kernel intervention and the other through
    77  * wq->missed_wakeups being 1.
    78  *
    79  * To mitigate this problem, futex_down_timeout() detects that the syscall
    80  * didn't sleep in the wait queue, fixes the futex counter and RETRIES the
    81  * whole operation again.
    82  */
    8339
    8440/** Initialize futex counter.
     
    9248}
    9349
    94 int futex_down(futex_t *futex)
    95 {
    96         return futex_down_timeout(futex, SYNCH_NO_TIMEOUT, SYNCH_FLAGS_NONE);
    97 }
    98 
    99 int futex_trydown(futex_t *futex)
    100 {
    101         return futex_down_timeout(futex, SYNCH_NO_TIMEOUT,
    102             SYNCH_FLAGS_NON_BLOCKING);
    103 }
    104 
    10550/** Try to down the futex.
    10651 *
    10752 * @param futex         Futex.
    108  * @param usec          Microseconds to wait. Zero value means sleep without
    109  *                      timeout.
    110  * @param flags         Select mode of operation. See comment for
    111  *                      waitq_sleep_timeout().
     53 * @return              Non-zero if the futex was acquired.
     54 * @return              Zero if the futex was not acquired.
     55 */
     56int futex_trydown(futex_t *futex)
     57{
     58        return cas(futex, 1, 0);
     59}
     60
     61/** Down the futex.
    11262 *
    113  * @return              ENOENT if there is no such virtual address. One of
    114  *                      ESYNCH_OK_ATOMIC and ESYNCH_OK_BLOCKED on success or
    115  *                      ESYNCH_TIMEOUT if the lock was not acquired because of
    116  *                      a timeout or ESYNCH_WOULD_BLOCK if the operation could
    117  *                      not be carried out atomically (if requested so).
     63 * @param futex         Futex.
     64 * @return              ENOENT if there is no such virtual address.
     65 * @return              Zero in the uncontended case.
     66 * @return              Otherwise one of ESYNCH_OK_ATOMIC or ESYNCH_OK_BLOCKED.
    11867 */
    119 int futex_down_timeout(futex_t *futex, uint32_t usec, int flags)
     68int futex_down(futex_t *futex)
    12069{
    121         int rc;
    122        
    123         while (atomic_predec(futex) < 0) {
    124                 rc = __SYSCALL3(SYS_FUTEX_SLEEP, (sysarg_t) &futex->count,
    125                     (sysarg_t) usec, (sysarg_t) flags);
    126                
    127                 switch (rc) {
    128                 case ESYNCH_OK_ATOMIC:
    129                         /*
    130                          * Because of a race condition between timeout and
    131                          * futex_up() and between conditional
    132                          * futex_down_timeout() and futex_up(), we have to give
    133                          * up and try again in this special case.
    134                          */
    135                         atomic_inc(futex);
    136                         break;
     70        if (atomic_predec(futex) < 0)
     71                return __SYSCALL1(SYS_FUTEX_SLEEP, (sysarg_t) &futex->count);
    13772
    138                 case ESYNCH_TIMEOUT:
    139                         atomic_inc(futex);
    140                         return ESYNCH_TIMEOUT;
    141                         break;
    142 
    143                 case ESYNCH_WOULD_BLOCK:
    144                         /*
    145                          * The conditional down operation should be implemented
    146                          * this way. The userspace-only variant tends to
    147                          * accumulate missed wakeups in the kernel futex wait
    148                          * queue.
    149                          */
    150                         atomic_inc(futex);
    151                         return ESYNCH_WOULD_BLOCK;
    152                         break;
    153 
    154                 case ESYNCH_OK_BLOCKED:
    155                         /*
    156                          * Enter the critical section.
    157                          * The futex counter has already been incremented for
    158                          * us.
    159                          */
    160                         return ESYNCH_OK_BLOCKED;
    161                         break;
    162                 default:
    163                         return rc;
    164                 }
    165         }
    166 
    167         /*
    168          * Enter the critical section.
    169          */
    170         return ESYNCH_OK_ATOMIC;
     73        return 0;
    17174}
    17275
     
    17477 *
    17578 * @param futex         Futex.
    176  *
    177  * @return              ENOENT if there is no such virtual address. Otherwise
    178  *                      zero.
     79 * @return              ENOENT if there is no such virtual address.
     80 * @return              Zero in the uncontended case.
    17981 */
    18082int futex_up(futex_t *futex)
    18183{
    182         long val;
    183        
    184         val = atomic_postinc(futex);
    185         if (val < 0)
     84        if (atomic_postinc(futex) < 0)
    18685                return __SYSCALL1(SYS_FUTEX_WAKEUP, (sysarg_t) &futex->count);
    18786               
  • uspace/lib/libc/generic/io/console.c

    r58d5803d r387416b  
    9494}
    9595
     96int console_get_pos(int phone, int *col, int *row)
     97{
     98        ipcarg_t col_v;
     99        ipcarg_t row_v;
     100        int rc;
     101
     102        rc = async_req_0_2(phone, CONSOLE_GET_POS, &col_v, &row_v);
     103
     104        *col = (int) col_v;
     105        *row = (int) row_v;
     106        return rc;
     107}
     108
    96109void console_goto(int phone, int col, int row)
    97110{
  • uspace/lib/libc/generic/io/io.c

    r58d5803d r387416b  
    341341size_t fread(void *buf, size_t size, size_t nmemb, FILE *stream)
    342342{
    343         size_t left = size * nmemb;
    344         size_t done = 0;
    345        
     343        size_t left, done;
     344
     345        if (size == 0 || nmemb == 0)
     346                return 0;
     347
    346348        /* Make sure no data is pending write. */
    347349        _fflushbuf(stream);
     350
     351        left = size * nmemb;
     352        done = 0;
    348353       
    349354        while ((left > 0) && (!stream->error) && (!stream->eof)) {
     
    365370static size_t _fwrite(const void *buf, size_t size, size_t nmemb, FILE *stream)
    366371{
    367         size_t left = size * nmemb;
    368         size_t done = 0;
    369        
     372        size_t left;
     373        size_t done;
     374
     375        if (size == 0 || nmemb == 0)
     376                return 0;
     377
     378        left = size * nmemb;
     379        done = 0;
     380
    370381        while ((left > 0) && (!stream->error)) {
    371382                ssize_t wr;
     
    421432        uint8_t b;
    422433        bool need_flush;
    423        
     434
     435        if (size == 0 || nmemb == 0)
     436                return 0;
     437
    424438        /* If not buffered stream, write out directly. */
    425439        if (stream->btype == _IONBF) {
     
    480494       
    481495        if (chr_encode(c, buf, &sz, STR_BOUNDS(1)) == EOK) {
    482                 size_t wr = fwrite(buf, sz, 1, stream);
     496                size_t wr = fwrite(buf, 1, sz, stream);
    483497               
    484498                if (wr < sz)
  • uspace/lib/libc/generic/string.c

    r58d5803d r387416b  
    471471 * null-terminated and containing only complete characters.
    472472 *
    473  * @param dst   Destination buffer.
     473 * @param dest   Destination buffer.
    474474 * @param count Size of the destination buffer (must be > 0).
    475475 * @param src   Source string.
     
    505505 * have to be null-terminated.
    506506 *
    507  * @param dst   Destination buffer.
     507 * @param dest   Destination buffer.
    508508 * @param count Size of the destination buffer (must be > 0).
    509509 * @param src   Source string.
     
    537537 * null-terminated and containing only complete characters.
    538538 *
    539  * @param dst   Destination buffer.
     539 * @param dest   Destination buffer.
    540540 * @param count Size of the destination buffer.
    541541 * @param src   Source string.
     
    549549}
    550550
    551 /** Copy NULL-terminated wide string to string
    552  *
    553  * Copy source wide string @a src to destination buffer @a dst.
    554  * No more than @a size bytes are written. NULL-terminator is always
    555  * written after the last succesfully copied character (i.e. if the
    556  * destination buffer is has at least 1 byte, it will be always
    557  * NULL-terminated).
    558  *
    559  * @param src   Source wide string.
    560  * @param dst   Destination buffer.
    561  * @param count Size of the destination buffer.
    562  *
    563  */
    564 void wstr_nstr(char *dst, const wchar_t *src, size_t size)
    565 {
    566         /* No space for the NULL-terminator in the buffer */
    567         if (size == 0)
    568                 return;
    569        
     551/** Convert wide string to string.
     552 *
     553 * Convert wide string @a src to string. The output is written to the buffer
     554 * specified by @a dest and @a size. @a size must be non-zero and the string
     555 * written will always be well-formed.
     556 *
     557 * @param dest  Destination buffer.
     558 * @param size  Size of the destination buffer.
     559 * @param src   Source wide string.
     560 */
     561void wstr_to_str(char *dest, size_t size, const wchar_t *src)
     562{
    570563        wchar_t ch;
    571         size_t src_idx = 0;
    572         size_t dst_off = 0;
    573        
     564        size_t src_idx;
     565        size_t dest_off;
     566
     567        /* There must be space for a null terminator in the buffer. */
     568        assert(size > 0);
     569       
     570        src_idx = 0;
     571        dest_off = 0;
     572
    574573        while ((ch = src[src_idx++]) != 0) {
    575                 if (chr_encode(ch, dst, &dst_off, size) != EOK)
     574                if (chr_encode(ch, dest, &dest_off, size - 1) != EOK)
    576575                        break;
    577576        }
    578        
    579         if (dst_off >= size)
    580                 dst[size - 1] = 0;
    581         else
    582                 dst[dst_off] = 0;
     577
     578        dest[dest_off] = '\0';
     579}
     580
     581/** Convert wide string to new string.
     582 *
     583 * Convert wide string @a src to string. Space for the new string is allocated
     584 * on the heap.
     585 *
     586 * @param src   Source wide string.
     587 * @return      New string.
     588 */
     589char *wstr_to_astr(const wchar_t *src)
     590{
     591        char dbuf[STR_BOUNDS(1)];
     592        char *str;
     593        wchar_t ch;
     594
     595        size_t src_idx;
     596        size_t dest_off;
     597        size_t dest_size;
     598
     599        /* Compute size of encoded string. */
     600
     601        src_idx = 0;
     602        dest_size = 0;
     603
     604        while ((ch = src[src_idx++]) != 0) {
     605                dest_off = 0;
     606                if (chr_encode(ch, dbuf, &dest_off, STR_BOUNDS(1)) != EOK)
     607                        break;
     608                dest_size += dest_off;
     609        }
     610
     611        str = malloc(dest_size + 1);
     612        if (str == NULL)
     613                return NULL;
     614
     615        /* Encode string. */
     616
     617        src_idx = 0;
     618        dest_off = 0;
     619
     620        while ((ch = src[src_idx++]) != 0) {
     621                if (chr_encode(ch, str, &dest_off, dest_size) != EOK)
     622                        break;
     623        }
     624
     625        str[dest_size] = '\0';
     626        return str;
     627}
     628
     629
     630/** Convert string to wide string.
     631 *
     632 * Convert string @a src to wide string. The output is written to the
     633 * buffer specified by @a dest and @a dlen. @a dlen must be non-zero
     634 * and the wide string written will always be null-terminated.
     635 *
     636 * @param dest  Destination buffer.
     637 * @param dlen  Length of destination buffer (number of wchars).
     638 * @param src   Source string.
     639 */
     640void str_to_wstr(wchar_t *dest, size_t dlen, const char *src)
     641{
     642        size_t offset;
     643        size_t di;
     644        wchar_t c;
     645
     646        assert(dlen > 0);
     647
     648        offset = 0;
     649        di = 0;
     650
     651        do {
     652                if (di >= dlen - 1)
     653                        break;
     654
     655                c = str_decode(src, &offset, STR_NO_LIMIT);
     656                dest[di++] = c;
     657        } while (c != '\0');
     658
     659        dest[dlen - 1] = '\0';
    583660}
    584661
  • uspace/lib/libc/generic/time.c

    r58d5803d r387416b  
    3131 */
    3232/** @file
    33  */ 
     33 */
    3434
    3535#include <sys/time.h>
     
    4040#include <unistd.h>
    4141#include <atomic.h>
    42 #include <futex.h>
    4342#include <sysinfo.h>
    4443#include <ipc/services.h>
     44#include <libc.h>
    4545
    4646#include <sysinfo.h>
     
    189189
    190190/** Wait unconditionally for specified number of microseconds */
    191 int usleep(unsigned long usec)
    192 {
    193         atomic_t futex = FUTEX_INITIALIZER;
    194 
    195         futex_initialize(&futex, 0);
    196         futex_down_timeout(&futex, usec, 0);
     191int usleep(useconds_t usec)
     192{
     193        (void) __SYSCALL1(SYS_THREAD_USLEEP, usec);
    197194        return 0;
    198195}
    199196
    200197/** Wait unconditionally for specified number of seconds */
    201 unsigned int sleep(unsigned int seconds)
    202 {
    203         atomic_t futex = FUTEX_INITIALIZER;
    204 
    205         futex_initialize(&futex, 0);
    206        
     198unsigned int sleep(unsigned int sec)
     199{
    207200        /* Sleep in 1000 second steps to support
    208201           full argument range */
    209         while (seconds > 0) {
    210                 unsigned int period = (seconds > 1000) ? 1000 : seconds;
     202        while (sec > 0) {
     203                unsigned int period = (sec > 1000) ? 1000 : sec;
    211204       
    212                 futex_down_timeout(&futex, period * 1000000, 0);
    213                 seconds -= period;
     205                usleep(period * 1000000);
     206                sec -= period;
    214207        }
    215208        return 0;
  • uspace/lib/libc/include/atomic.h

    r58d5803d r387416b  
    11/*
    2  * Copyright (c) 2006 Jakub Jermar
     2 * Copyright (c) 2009 Jakub Jermar
    33 * All rights reserved.
    44 *
     
    3636#define LIBC_ATOMIC_H_
    3737
    38 typedef struct atomic {
    39         volatile long count;
    40 } atomic_t;
    41 
    4238#include <libarch/atomic.h>
    43 
    44 static inline void atomic_set(atomic_t *val, long i)
    45 {
    46         val->count = i;
    47 }
    48 
    49 static inline long atomic_get(atomic_t *val)
    50 {
    51         return val->count;
    52 }
    5339
    5440#endif
  • uspace/lib/libc/include/fibril_synch.h

    r58d5803d r387416b  
    3333 */
    3434
    35 #ifndef LIBC_FIBRIL_SYNC_H_
    36 #define LIBC_FIBRIL_SYNC_H_
     35#ifndef LIBC_FIBRIL_SYNCH_H_
     36#define LIBC_FIBRIL_SYNCH_H_
    3737
    3838#include <async.h>
  • uspace/lib/libc/include/futex.h

    r58d5803d r387416b  
    4646extern int futex_down(futex_t *futex);
    4747extern int futex_trydown(futex_t *futex);
    48 extern int futex_down_timeout(futex_t *futex, uint32_t usec, int flags);
    4948extern int futex_up(futex_t *futex);
    5049
  • uspace/lib/libc/include/io/console.h

    r58d5803d r387416b  
    6969
    7070extern int console_get_size(int phone, int *cols, int *rows);
     71extern int console_get_pos(int phone, int *col, int *row);
    7172extern void console_goto(int phone, int col, int row);
    7273
  • uspace/lib/libc/include/ipc/console.h

    r58d5803d r387416b  
    4343        CONSOLE_GET_COLOR_CAP,
    4444        CONSOLE_GET_EVENT,
     45        CONSOLE_GET_POS,
    4546        CONSOLE_GOTO,
    4647        CONSOLE_CLEAR,
  • uspace/lib/libc/include/ipc/services.h

    r58d5803d r387416b  
    4747        SERVICE_DEVMAP,
    4848        SERVICE_FHC,
    49         SERVICE_OBIO
     49        SERVICE_OBIO,
     50        SERVICE_CLIPBOARD
    5051} services_t;
    5152
  • uspace/lib/libc/include/string.h

    r58d5803d r387416b  
    7373extern void str_append(char *dest, size_t size, const char *src);
    7474
    75 extern void wstr_nstr(char *dst, const wchar_t *src, size_t size);
     75extern void wstr_to_str(char *dest, size_t size, const wchar_t *src);
     76extern char *wstr_to_astr(const wchar_t *src);
     77extern void str_to_wstr(wchar_t *dest, size_t dlen, const char *src);
    7678
    7779extern char *str_chr(const char *str, wchar_t ch);
  • uspace/lib/libc/include/unistd.h

    r58d5803d r387416b  
    5151#endif
    5252
     53typedef uint32_t useconds_t;
     54
    5355extern int dup2(int oldfd, int newfd);
    5456
     
    6870
    6971extern void _exit(int status) __attribute__ ((noreturn));
    70 extern int usleep(unsigned long usec);
    71 extern unsigned int sleep(unsigned int seconds);
     72extern int usleep(useconds_t uses);
     73extern unsigned int sleep(unsigned int se);
    7274
    7375#endif
  • uspace/srv/bd/ata_bd/ata_bd.c

    r58d5803d r387416b  
    5555#include <async.h>
    5656#include <as.h>
    57 #include <fibril_sync.h>
     57#include <fibril_synch.h>
    5858#include <string.h>
    5959#include <devmap.h>
  • uspace/srv/bd/ata_bd/ata_bd.h

    r58d5803d r387416b  
    3737
    3838#include <sys/types.h>
    39 #include <fibril_sync.h>
     39#include <fibril_synch.h>
    4040#include <string.h>
    4141
    4242enum {
    43         CTL_READ_START  = 0,
     43        CTL_READ_START  = 0,
    4444        CTL_WRITE_START = 1,
    4545};
    4646
    4747enum {
    48         STATUS_FAILURE  = 0
     48        STATUS_FAILURE = 0
    4949};
    5050
  • uspace/srv/bd/file_bd/file_bd.c

    r58d5803d r387416b  
    4545#include <async.h>
    4646#include <as.h>
    47 #include <fibril_sync.h>
     47#include <fibril_synch.h>
    4848#include <devmap.h>
    4949#include <sys/types.h>
  • uspace/srv/bd/gxe_bd/gxe_bd.c

    r58d5803d r387416b  
    4343#include <async.h>
    4444#include <as.h>
    45 #include <fibril_sync.h>
     45#include <fibril_synch.h>
    4646#include <devmap.h>
    4747#include <sys/types.h>
  • uspace/srv/bd/rd/rd.c

    r58d5803d r387416b  
    5151#include <align.h>
    5252#include <async.h>
    53 #include <fibril_sync.h>
     53#include <fibril_synch.h>
    5454#include <stdio.h>
    5555#include <devmap.h>
  • uspace/srv/console/console.c

    r58d5803d r387416b  
    5050#include <event.h>
    5151#include <devmap.h>
    52 #include <fibril_sync.h>
     52#include <fibril_synch.h>
    5353
    5454#include "console.h"
     
    601601                                    IPC_GET_ARG2(call));
    602602                        break;
     603                case CONSOLE_GET_POS:
     604                        arg1 = cons->scr.position_x;
     605                        arg2 = cons->scr.position_y;
     606                        break;
    603607                case CONSOLE_GET_SIZE:
    604608                        arg1 = fb_info.cols;
  • uspace/srv/devmap/devmap.c

    r58d5803d r387416b  
    4242#include <errno.h>
    4343#include <bool.h>
    44 #include <fibril_sync.h>
     44#include <fibril_synch.h>
    4545#include <stdlib.h>
    4646#include <string.h>
     
    867867}
    868868
    869 /** 
     869/**
    870870 * @}
    871871 */
  • uspace/srv/fs/devfs/devfs_ops.c

    r58d5803d r387416b  
    4242#include <string.h>
    4343#include <libfs.h>
    44 #include <fibril_sync.h>
     44#include <fibril_synch.h>
    4545#include <adt/hash_table.h>
    4646#include <sys/stat.h>
  • uspace/srv/fs/fat/fat.h

    r58d5803d r387416b  
    3636#include "fat_fat.h"
    3737#include <ipc/ipc.h>
    38 #include <fibril_sync.h>
     38#include <fibril_synch.h>
    3939#include <libfs.h>
    4040#include <atomic.h>
  • uspace/srv/fs/fat/fat_fat.c

    r58d5803d r387416b  
    4646#include <align.h>
    4747#include <assert.h>
    48 #include <fibril_sync.h>
     48#include <fibril_synch.h>
    4949#include <mem.h>
    5050
  • uspace/srv/fs/fat/fat_idx.c

    r58d5803d r387416b  
    4343#include <adt/list.h>
    4444#include <assert.h>
    45 #include <fibril_sync.h>
     45#include <fibril_synch.h>
    4646
    4747/** Each instance of this type describes one interval of freed VFS indices. */
  • uspace/srv/fs/fat/fat_ops.c

    r58d5803d r387416b  
    5252#include <adt/list.h>
    5353#include <assert.h>
    54 #include <fibril_sync.h>
     54#include <fibril_synch.h>
    5555#include <sys/mman.h>
    5656#include <align.h>
  • uspace/srv/loader/arch/arm32/arm32.s

    r58d5803d r387416b  
    3636# Jump to a program entry point
    3737program_run:
     38        # load ras_page address to r2
     39        ldr r2, =ras_page
     40        ldr r2, [r2]
    3841        # pcb is passed to the entry point in r1 (where it already is)
    3942        mov r15, r0
  • uspace/srv/part/mbr_part/mbr_part.c

    r58d5803d r387416b  
    6161#include <async.h>
    6262#include <as.h>
    63 #include <fibril_sync.h>
     63#include <fibril_synch.h>
    6464#include <devmap.h>
    6565#include <sys/types.h>
  • uspace/srv/vfs/vfs.h

    r58d5803d r387416b  
    3636#include <ipc/ipc.h>
    3737#include <adt/list.h>
    38 #include <fibril_sync.h>
     38#include <fibril_synch.h>
    3939#include <sys/types.h>
    4040#include <devmap.h>
  • uspace/srv/vfs/vfs_file.c

    r58d5803d r387416b  
    4242#include <bool.h>
    4343#include <fibril.h>
    44 #include <fibril_sync.h>
     44#include <fibril_synch.h>
    4545#include "vfs.h"
    4646
  • uspace/srv/vfs/vfs_lookup.c

    r58d5803d r387416b  
    4343#include <stdarg.h>
    4444#include <bool.h>
    45 #include <fibril_sync.h>
     45#include <fibril_synch.h>
    4646#include <adt/list.h>
    4747#include <vfs/canonify.h>
  • uspace/srv/vfs/vfs_node.c

    r58d5803d r387416b  
    3939#include <stdlib.h>
    4040#include <string.h>
    41 #include <fibril_sync.h>
     41#include <fibril_synch.h>
    4242#include <adt/hash_table.h>
    4343#include <assert.h>
  • uspace/srv/vfs/vfs_ops.c

    r58d5803d r387416b  
    4444#include <string.h>
    4545#include <bool.h>
    46 #include <fibril_sync.h>
     46#include <fibril_synch.h>
    4747#include <adt/list.h>
    4848#include <unistd.h>
  • uspace/srv/vfs/vfs_register.c

    r58d5803d r387416b  
    4646#include <ctype.h>
    4747#include <bool.h>
    48 #include <fibril_sync.h>
     48#include <fibril_synch.h>
    4949#include <adt/list.h>
    5050#include <as.h>
Note: See TracChangeset for help on using the changeset viewer.