コード例 #1
0
void
fixed_gap_arena_insert(FixedGapArena *arena,
                       memi offset,
                       const ch8 *data,
                       memi size)
{
    // TODO: In case we can take ownership of data, we can just wrap it with gap buffers and be done.
    // TODO: In case we cannot take ownership of data, but the data is persistent, we can wrap it with copy-on-write gap buffers.

    // TODO: Remove the checks.
    if (size == 0) {
        return;
    }
    hale_assert(offset <= arena->size);
    hale_assert_debug(vector_count(arena->buffers));

    Buf *it0 = find_buf_GTE(arena,
                       &offset,
                       vector_begin(&arena->buffers),
                       vector_end(&arena->buffers));

    // Move these to tests.
    hale_assert_requirement(it0);
    // hale_assert(buf_length(it) != 0);
    hale_assert(buf_length(it0) >= offset);

    if (buf_available(it0) >= size) {
        buf_insert(it0, offset, data, size);
    } else {
        insert_non_crit_branch(arena, offset, data, size, it0);
    }

    arena->size += size;
}
コード例 #2
0
ファイル: cmdline_mode.c プロジェクト: isbadawi/badavi
static void cmdline_mode_key_pressed(struct editor *editor, struct tb_event *ev) {
  char ch;
  struct cmdline_mode *mode = (struct cmdline_mode*) editor->mode;
  switch (ev->key) {
  case TB_KEY_ESC: case TB_KEY_CTRL_C:
    buf_clear(editor->status);
    editor_pop_mode(editor);
    return;
  // FIXME(ibadawi): termbox doesn't support shift + arrow keys.
  // vim uses <S-Left>, <S-Right> for moving cursor to prev/next WORD.
  case TB_KEY_ARROW_LEFT:
    editor->status_cursor = max(editor->status_cursor - 1, 1);
    return;
  case TB_KEY_ARROW_RIGHT:
    editor->status_cursor = min(editor->status_cursor + 1, editor->status->len);
    return;
  case TB_KEY_CTRL_B: case TB_KEY_HOME:
    editor->status_cursor = 1;
    return;
  case TB_KEY_CTRL_E: case TB_KEY_END:
    editor->status_cursor = editor->status->len;
    return;
  case TB_KEY_BACKSPACE2:
    buf_delete(editor->status, --editor->status_cursor, 1);
    if (editor->status->len == 0) {
      editor_pop_mode(editor);
      return;
    } else if (mode->char_cb) {
      char *command = xstrdup(editor->status->buf + 1);
      mode->char_cb(editor, command);
      free(command);
    }
    return;
  case TB_KEY_ENTER: {
    char *command = xstrdup(editor->status->buf + 1);
    editor_pop_mode(editor);
    mode->done_cb(editor, command);
    free(command);
    return;
  }
  case TB_KEY_SPACE:
    ch = ' ';
    break;
  default:
    ch = (char) ev->ch;
  }
  char s[2] = {ch, '\0'};
  buf_insert(editor->status, s, editor->status_cursor++);
  if (mode->char_cb) {
    char *command = xstrdup(editor->status->buf + 1);
    mode->char_cb(editor, command);
    free(command);
  }
}
コード例 #3
0
ファイル: gesave.c プロジェクト: Refandler/gentee
void STDCALL gesave_finish( void )
{
   buf  bt;
   pbuf pb = gesave;
   uint size = buf_len( pb ) - gesaveoff;

   if ( size <= 187 )
      *( pubyte )(( pubyte )buf_ptr( gesave ) + gesaveoff + 5 ) = ( ubyte )size;
   else
   {
      buf_init( &bt );
      gesave = &bt;
      if ( size < 16800 )
      {
         size++;
         gesave_bwdi( size );
      }
      else
         if ( size < 0xFFF0 ) 
         {
            gesave_addubyte( 0xFE );
            size += 2;
            gesave_addushort( size );
         }
         else
         {
            gesave_addubyte( 0xFF );
            size += 4;
            gesave_adduint( size );
         }
      // Write the size
      // We have already had one byte, so -1
      buf_insert( pb, gesaveoff + 5, ( pubyte )&size /*any*/, buf_len( gesave ) - 1 );
      mem_copy( buf_ptr( pb ) + gesaveoff + 5, buf_ptr( gesave ), buf_len( gesave ));

      buf_delete( &bt );
      gesave = pb;
   }
}
コード例 #4
0
ファイル: gesave.c プロジェクト: Refandler/gentee
void STDCALL gesave_finish( pvmEngine pThis )
{
   buf  bt;
   pbuf pb = pThis->gesave;
   uint size = buf_len( pThis, pb ) - pThis->gesaveoff;

   if ( size <= 187 )
      *( pubyte )(( pubyte )buf_ptr( pThis, pThis->gesave ) + pThis->gesaveoff + 5 ) = ( ubyte )size;
   else
   {
      buf_init( pThis, &bt );
      pThis->gesave = &bt;
      if ( size < 16800 )
      {
         size++;
         gesave_bwd( pThis, size );
      }
      else
         if ( size < 0xFFF0 ) 
         {
            gesave_addubyte( pThis, 0xFE );
            size += 2;
            gesave_addushort( pThis, size );
         }
         else
         {
            gesave_addubyte( pThis, 0xFF );
            size += 4;
            gesave_adduint( pThis, size );
         }
      // Write the size
      // We have already had one byte, so -1
      buf_insert( pThis, pb, pThis->gesaveoff + 5, ( pubyte )&size /*any*/, buf_len( pThis, pThis->gesave ) - 1 );
      mem_copy( pThis, buf_ptr( pThis, pb ) + pThis->gesaveoff + 5, buf_ptr( pThis, pThis->gesave ), buf_len( pThis, pThis->gesave ));

      buf_delete( pThis, &bt );
      pThis->gesave = pb;
   }
}
コード例 #5
0
ファイル: buf.c プロジェクト: isbadawi/badavi
void buf_append(struct buf *buf, char *s) {
  buf_insert(buf, s, buf->len);
}
コード例 #6
0
hale_internal
void
insert_non_crit_branch(FixedGapArena *arena,
                       memi offset,
                       const ch8 *data,
                       memi size,
                       Buf *it0)
{
    requirement_check_buf(it0);

    Buf *it1 = NULL;

    // TODO: Merge the `it` with next and previous buffers.

    // [...**]
    //     ^^----suffix----vv
    // [..+++] [+++++] [+++**]
    //    ^^^   ^^^^^   ^^^
    //    +++   +++++   +++**
    //    p0      p1     p2 ^-sx

    // http://cpp.sh/9yp22

    // Copy to first (possible split)
    memi p0 = hale_minimum(buf_capacity - offset, size);
    // Copy to new buffers (full)
    memi p1 = (size-p0) & ~buf_align_mask;
    // Copy to last (partial)
    memi p2 = (size-p0) &  buf_align_mask; // same as (data_size - r.p1 - r.p0);
    // Split size (won't underflow, as offset must be within the block (or == buf_length))
    memi sx = buf_length(it0) - offset;

    hale_assert(p0 + p1 + p2 == size);

    // TODO: Check if we can put part of `p1`, `p2` into sx.
    // - `p1` probably makes no sense to be merged with sx, as it's already calculated to be full.

    memi n = 0;
    // if (p0 && sx) { n += 1; }
    n += p0 && sx;
    // if (p1)       { n += p1 >> buf_capacity_shift; }
    n += p1 >> buf_align_shift;
    // if (p2)       { n += 1; }
    n += !!p2;

    if (n) {
        it1 = allocate_buffers(arena, buf_index(arena, it0) + 1, n);
        // TODO: This wouldn't be needed if allocate_buffers wouldn't
        // invalidate the pointers. (deque?)
        it0 = it1 - 1;
    }

    if (p0) {
        if (sx) {
            hale_assert_requirement(n != 0)
            buf_move_suffix(it0, offset, it0 + n); // same as `it1 + n - 1`
        }
        buf_insert(it0, offset, data, p0);

        // `data` and `size` is used in `p1` and `p2`,
        // so we update he right away.
        data += p0;
        size -= p0;
    }

    if (p1)
    {
        hale_assert_debug(it1);

        while (size != p2)
        {
            // TODO: buf_set
            buf_insert(it1, 0, data, buf_capacity);
            data += buf_capacity;
            size -= buf_capacity;
            ++it1;
        }
    }

    if (p2) {
        hale_assert_requirement(it1);
        hale_assert_requirement(p2 == size);
        // TODO: buf_set
        buf_insert(it1, 0, data, p2);
    }
}