Пример #1
0
/**
 * Using VMT's with keys (like environment-variables)
 *
 * gets a variable's value
 * if variable not found, returns NULL otherwise returns a newly created string with the value
 */
char *dbt_getvar(dbt_t fh, const char *varname) {
  char *buf, *retval = NULL;
  int i;
  dbt_var_t nd;

  // find if already exists
  for (i = 0; i < dbt_count(fh); i++) {
    char *nd_var, *nd_val;

    // load the record
    dbt_read(fh, i, &nd, sizeof(nd));
    if (nd.sign == dbt_var_sign) {
      buf = tmp_alloc(nd.node_len);
      dbt_read(fh, i, buf, nd.node_len);
      nd_var = buf + sizeof(nd);
      nd_val = buf + sizeof(nd) + nd.var_len;

      // check varname
      if (strcmp(nd_var, varname) == 0) {
        retval = tmp_strdup(nd_val);
        tmp_free(buf);
        break;
      }

      tmp_free(buf);
    }
  }

  return retval;
}
Пример #2
0
/*
 *converts the variable to string-variable
 */
void v_tostr(var_t *arg) {
  if (arg->type != V_STR) {
    char *tmp;
    int l;

    tmp = tmp_alloc(64);

    switch (arg->type) {
    case V_UDS:
      break;
    case V_PTR:
      //ltostr(arg->v.ap.p, tmp);
      break;
    case V_INT:
      //ltostr(arg->v.i, tmp);
      break;
    case V_NUM:
      //ftostr(arg->v.n, tmp);
      break;
    default:
      //err_varisarray();
      tmp_free(tmp);
      return;
    }

    l = strlen(tmp) + 1;
    arg->type = V_STR;
    arg->v.p.ptr = tmp_alloc(l);
    arg->v.p.size = l;
    strcpy(arg->v.p.ptr, tmp);
    tmp_free(tmp);
  }
}
Пример #3
0
/*
 *release variable
 */
void v_free(var_t *v) {
  int i;
  var_t *elem;

  switch (v->type) {
  case V_STR:
    if (v->v.p.ptr) {
      tmp_free(v->v.p.ptr);
    }
    v->v.p.ptr = NULL;
    v->v.p.size = 0;
    break;
  case V_ARRAY:
    if (v->v.a.size) {
      if (v->v.a.ptr) {
        for (i = 0; i < v->v.a.size; i++) {
          elem = (var_t *) (v->v.a.ptr + (sizeof(var_t) *i));
          v_free(elem);
        }

        tmp_free(v->v.a.ptr);
        v->v.a.ptr = NULL;
        v->v.a.size = 0;
      }
    }
    break;
  case V_UDS:
    break;
  }

  v_init(v);
}
Пример #4
0
/**
 * Using VMT's with keys (like environment-variables)
 *
 * sets a variable
 *
 * if varvalue == NULL, the variable will be deleted
 */
int dbt_setvar(dbt_t fh, const char *varname, const char *varvalue) {
  char *buf, *newrec = NULL;
  int i, idx;
  dbt_var_t nd, new_nd;

  if (varvalue) {
    // create the new header
    new_nd.sign = dbt_var_sign;
    new_nd.var_len = strlen(varname) + 1;
    new_nd.val_len = strlen(varvalue) + 1;
    new_nd.node_len = sizeof(new_nd) + new_nd.var_len + new_nd.val_len;

    // create record
    newrec = tmp_alloc(new_nd.node_len);
    memcpy(newrec, &new_nd, sizeof(new_nd));
    memcpy(newrec + sizeof(new_nd), varname, new_nd.var_len);
    memcpy(newrec + sizeof(new_nd) + new_nd.var_len, varvalue, new_nd.val_len);
  }

  // default index (new record)
  idx = dbt_count(fh);

  // find if already exists
  for (i = 0; i < dbt_count(fh); i++) {
    char *nd_var, *nd_val;

    // load the record
    dbt_read(fh, i, &nd, sizeof(nd));
    if (nd.sign == dbt_var_sign) {
      buf = tmp_alloc(nd.node_len);
      dbt_read(fh, i, buf, nd.node_len);
      nd_var = buf + sizeof(nd);
      nd_val = buf + sizeof(nd) + nd.var_len;

      // check varname
      if (strcmp(nd_var, varname) == 0) {
        idx = i;
        tmp_free(buf);
        break;
      }

      tmp_free(buf);
    }
  }

  if (varvalue) {
    // store the record
    dbt_write(fh, idx, newrec, new_nd.node_len);
    tmp_free(newrec);
  } else
    // delete the record
    dbt_remove(fh, idx);
  return 0;
}
Пример #5
0
/*
 * convert's a user's string to variable
 *
 * its decides in what format to store the value
 * its used mostly by 'input' functions
 */
void v_input2var(const char *str, var_t *var) {
  v_free(var);

  if (strlen(str) == 0) {       // no data
    v_setstr(var, str);
  } else {
    char *np, *sb;
    char buf[64];
    int type;
    var_int_t lv;
    var_num_t dv;

    sb = tmp_strdup(str);
    np = get_numexpr(sb, buf, &type, &lv, &dv);

    if (type == 1 && *np == '\0') {
      v_setint(var, lv);
    } else if (type == 2 && *np == '\0') {
      v_setreal(var, dv);
    } else {
      v_setstr(var, str);
    }
    tmp_free(sb);
  }
}
Пример #6
0
/**
 * allocates additional space on database for 'recs' records of 'recsize' size
 */
int dbt_file_append(dbt_t t, int recs, int recsize) {
  vmt_rec_t rec;
  int i;
  int n;

  rec.ver = 1;
  rec.size = recsize;

  // create empty records
  if (vmt[t].count + recs >= vmt[t].size) {
    int newsize;
    char *data;

    data = tmp_alloc(recsize);
    memset(data, 0, recsize);
    newsize = vmt[t].size + recs;

    for (i = vmt[t].size; i < newsize; i++) {
      lseek(vmt[t].i_handle, sizeof(vmt_rec_t) * i + sizeof(vmt_t), SEEK_SET);
      rec.offset = lseek(vmt[t].f_handle, 0, SEEK_END);
      n = write(vmt[t].i_handle, &rec, sizeof(vmt_rec_t));
      n = write(vmt[t].f_handle, data, recsize);
    }

    tmp_free(data);
    vmt[t].size = newsize;
  }

  vmt[t].count++;

  // 
  dbt_file_write_header(t);
  return vmt[t].count - 1;
}
Пример #7
0
/* handle_screenshots appends the screenshot to the video buffer */
int handle_screenshot(AVFormatContext *oc, AVStream *st,
                      struct SwsContext *s_ctx, int frame_count,
                      long time_interval, char* filepath, TouchActualizer *ta,
                      int fps, long base_time) {

    FFMPEG_tmp *tmp;
    AVFrame *in_frame;

    tmp = picture_to_frame(filepath);
    in_frame = tmp->frame;

    #ifdef DEBUG_FRAME
    printf("Begin writing picture\nCurrent frame: %d\n", frame_count);
    #endif

    frame_count = write_frame(oc, st, s_ctx, in_frame, ta,
            fps, frame_count, time_interval, base_time);
    tmp_free(tmp);

    #ifdef DEBUG_FRAME
    printf("End writing picture\nCurrent frame: %d\n", frame_count);
    #endif

    #ifdef DEBUG_FRAME
    printf("Read file %s and wrote interval %ld\n", filepath, time_interval);
    printf("Written %d frames\n", interval_to_frames(time_interval, 25));
    #endif

    return frame_count;
}
Пример #8
0
/*
 *set the value of 'var' to string
 */
void v_setstrf(var_t *var, const char *fmt, ...) {
  char *buf;
  va_list ap;

  va_start(ap, fmt);
  buf = tmp_alloc(1024);
  vsnprintf(buf, 1024, fmt, ap);
  v_setstr(var, buf);
  tmp_free(buf);
  va_end(ap);
}
Пример #9
0
/*
 * cleanup format-list
 */
void free_format() {
  int i;
  fmt_node_t *node;

  for (i = 0; i < fmt_count; i++) {
    node = &fmt_stack[i];
    tmp_free(node->fmt);
  }

  fmt_count = fmt_cur = 0;
}
Пример #10
0
/*
 * converts the variable to string-variable
 */
void v_tostr(var_t *arg) {
  if (arg->type != V_STR) {
    char *tmp;
    int l;

    tmp = tmp_alloc(64);

    switch (arg->type) {
    case V_UDS:
      uds_to_str(arg, tmp, 64);
      uds_free(arg);
      break;
    case V_HASH:
      hash_to_str(arg, tmp, 64);
      hash_free_var(arg);
      break;
    case V_PTR:
      ltostr(arg->v.ap.p, tmp);
      break;
    case V_INT:
      ltostr(arg->v.i, tmp);
      break;
    case V_NUM:
      ftostr(arg->v.n, tmp);
      break;
    default:
      err_varisarray();
      tmp_free(tmp);
      return;
    }

    l = strlen(tmp) + 1;
    arg->type = V_STR;
    arg->v.p.ptr = tmp_alloc(l);
    arg->v.p.size = l;
    strcpy(arg->v.p.ptr, tmp);
    tmp_free(tmp);
  }
}
Пример #11
0
/*
 * set the value of 'var' to string
 */
void v_setstrf(var_t *var, const char *fmt, ...) {
  char *buf;
  va_list ap;

  va_start(ap, fmt);
#if defined(OS_LIMITED)
    buf = tmp_alloc(1024);
#else
    buf = tmp_alloc(0x10000);
#endif
  vsnprintf(buf, 1024, fmt, ap);
  v_setstr(var, buf);
  tmp_free(buf);
  va_end(ap);
}
Пример #12
0
/**
 * removes deleted chuncks (defrag)
 */
void dbt_file_pack(dbt_t t) {
  vmt_rec_t rec;
  int i, idx_offset, new_h, new_offset, n;
  char *data;
  char old_db_name[OS_PATHNAME_SIZE];
  char new_db_name[OS_PATHNAME_SIZE];

  sprintf(old_db_name, "%s.dbt", vmt[t].base);
  sprintf(new_db_name, "%s-new.dbt", vmt[t].base);
  new_h = open(new_db_name, O_BINARY | O_RDWR);
  for (i = 0; i < vmt[t].size; i++) {
    // read original record data
    idx_offset = i * sizeof(vmt_rec_t) + sizeof(vmt_t);
    lseek(vmt[t].i_handle, idx_offset, SEEK_SET);

    // read data
    data = tmp_alloc(rec.size);
    lseek(vmt[t].f_handle, rec.offset, rec.size);
    n = read(vmt[t].f_handle, data, rec.size);

    // copy record
    new_offset = lseek(new_h, 0, SEEK_END);
    rec.offset = new_offset;
    n = write(new_h, data, rec.size);
    tmp_free(data);

    // update index
    n = write(vmt[t].i_handle, &rec, sizeof(vmt_rec_t));
  }

  // swap databases and reopen
  close(vmt[t].f_handle);
  remove(old_db_name);
  close(new_h);
  rename(new_db_name, old_db_name);
  vmt[t].f_handle = open(old_db_name, O_BINARY | O_RDWR);
}
Пример #13
0
static void
x_analyze(x_display *xdpy, int fam)
{
  int i, j, n, face, pixsize, nsizes;
  char *name;
  if (tmp_fonts) tmp_free();
  tmp_fonts = XListFonts(xdpy->dpy, pattern[((unsigned int)fam)>>2], 1024, &n);

  for (i=0 ; i<n ; i++) {
    name = x_face(tmp_fonts[i], &face);
    if (!name) continue;

    /* extract pixels field */
    pixsize = 0;
    if (name[0]!='*') while (name[0] && name[0]>='0' && name[0]<='9')
      pixsize = 10*pixsize + *(name++) - '0';
    else
      name++;
    if (name[0]!='-') continue;

    /* protect against superlong font names */
    if (!pixsize && strlen(tmp_fonts[i])>120) continue;

    face += fam;

    nsizes = xdpy->available[face].nsizes;
    if (x_lookup(pixsize, xdpy->available[face].sizes, nsizes)) continue;
    if (nsizes%12==0) {
      int *sizes = xdpy->available[face].sizes;
      char **names = xdpy->available[face].names;
      xdpy->available[face].sizes = p_realloc(sizes, sizeof(int)*(nsizes+12));
      if (!xdpy->available[face].sizes) {
        xdpy->available[face].sizes = sizes;
        return;
      }
      xdpy->available[face].names = p_realloc(names,sizeof(char*)*(nsizes+13));
      if (!xdpy->available[face].names) {
        xdpy->available[face].names = names;
        return;
      }
    }
    j = x_insert(pixsize, xdpy->available[face].sizes,
                 xdpy->available[face].names, nsizes);
    xdpy->available[face].nsizes++;
    if (pixsize) {
      xdpy->available[face].names[j] = p_strcpy(tmp_fonts[i]);
    } else {
      /* scalable font needs wildcard name */
      char nm[128], *pnm = nm;
      int n = 7;
      name = tmp_fonts[i];
      while (n--) while ((*(pnm++)= *(name++))!='-');
      /* skip over pixels, points fields */
      *(pnm++)= '*';   *(pnm++)= '-';  *(pnm++)= '*';   *(pnm++)= '-';
      for (n=2 ; n-- ;) while (name[0] && *(name++)!='-');
      /* copy hres, vres, spacing fields */
      for (n=3 ; n-- ;) while (name[0] && (*(pnm++)= *(name++))!='-');
      /* skip over average width field */
      *(pnm++)= '*';   *(pnm++)= '-';
      while (name[0] && *(name++)!='-');
      /* copy remainder (character set fields) */
      while ((*(pnm++)= *(name++)));
      xdpy->available[face].names[j] = p_strcpy(nm);
    }
  }

  tmp_free();
}
Пример #14
0
/*
 * The final format - create the format-list 
 * (that list it will be used later by fmt_printN and fmt_printS)
 *
 * '_' the next character is not belongs to format (simple string)
 */
void build_format(const char *fmt_cnst) {
  char *fmt;
  char *p;
  int nc;
#if     defined(OS_LIMITED)
  char buf[128], *b;
#else
  char buf[1024], *b;
#endif

  free_format();

  // backup of format
  fmt = tmp_alloc(strlen(fmt_cnst) + 1);
  strcpy(fmt, fmt_cnst);

  p = fmt;
  b = buf;
  nc = 0;
  while (*p) {
    switch (*p) {
    case '_':
      // store prev. buf
      *b = '\0';
      if (strlen(buf)) {
        fmt_addfmt(buf, 0);
      }
      // store the new
      buf[0] = *(p + 1);
      buf[1] = '\0';
      fmt_addfmt(buf, 0);
      b = buf;
      p++;
      break;
    case '-':
    case '+':
    case '^':
    case '0':
    case '#':
      // store prev. buf
      *b = '\0';
      if (strlen(buf)) {
        fmt_addfmt(buf, 0);
      }
      // get num-fmt
      p = fmt_getnumfmt(buf, p);
      fmt_addfmt(buf, 1);
      b = buf;
      nc = 1;
      break;
    case '&':
    case '!':
    case '\\':
      // store prev. buf
      *b = '\0';
      if (strlen(buf)) {
        fmt_addfmt(buf, 0);
      }
      // get str-fmt
      p = fmt_getstrfmt(buf, p);
      fmt_addfmt(buf, 2);
      b = buf;
      nc = 1;
      break;
    default:
      *b++ = *p;
    }

    if (*p) {
      if (nc) {                  // do not advance
        nc = 0;
      } else {
        p++;
      }
    }
  }

  // store prev. buf
  *b = '\0';
  if (strlen(buf)) {
    fmt_addfmt(buf, 0);
  }
  // cleanup
  tmp_free(fmt);
}
Пример #15
0
/*
 * format: format a number
 *
 * symbols:
 *   # = digit or space
 *   0 = digit or zero
 *   ^ = exponential digit/format
 *   . = decimal point
 *   , = thousands
 *   - = minus for negative
 *   + = sign of number
 */
void format_num(char *dest, const char *fmt_cnst, var_num_t x) {
  char *p, *fmt;
  char left[64], right[64];
  char lbuf[64], rbuf[64];
  int dp = 0, lc = 0, sign = 0;
  int rsz, lsz;

  // backup of format
  fmt = tmp_alloc(strlen(fmt_cnst) + 1);
  strcpy(fmt, fmt_cnst);

  // check sign
  if (strchr(fmt, '-') || strchr(fmt, '+')) {
    sign = 1;
    if (x < 0.0) {
      sign = -1;
      x = -x;
    }
  }

  if (strchr(fmt_cnst, '^')) {
    // 
    // E format
    // 

    lc = fmt_cdig(fmt);
    if (lc < 4) {
      fmt_omap(dest, fmt);
      tmp_free(fmt);
      return;
    }

    // convert
    expfta(x, dest);

    // format
    p = strchr(dest, 'E');
    if (p) {
      *p = '\0';
      strcpy(left, dest);
      strcpy(right, p + 1);
      lsz = strlen(left);
      rsz = strlen(right) + 1;

      if (lc < rsz + 1) {
        fmt_omap(dest, fmt);
        tmp_free(fmt);
        return;
      }

      if (lc < lsz + rsz + 1)
        left[lc - rsz] = '\0';

      strcpy(lbuf, left);
      strcat(lbuf, "E");
      strcat(lbuf, right);
      fmt_nmap(-1, dest, fmt, lbuf);
    } else {
      strcpy(left, dest);
      fmt_nmap(-1, dest, fmt, left);
    }
  } else {
    // 
    // normal format
    // 

    // rounding
    p = strchr(fmt, '.');
    if (p) {
      x = fround(x, fmt_cdig(p + 1));
    } else {
      x = fround(x, 0);
    }

    // convert
    bestfta(x, dest);
    if (strchr(dest, 'E')) {
      fmt_omap(dest, fmt);
      tmp_free(fmt);
      return;
    }

    // left & right parts
    left[0] = right[0] = '\0';
    p = strchr(dest, '.');
    if (p) {
      *p = '\0';
      strcpy(right, p + 1);
    }
    strcpy(left, dest);

    // map format
    rbuf[0] = lbuf[0] = '\0';
    p = strchr(fmt, '.');
    if (p) {
      dp = 1;
      *p = '\0';
      fmt_nmap(1, rbuf, p + 1, right);
    }

    lc = fmt_cdig(fmt);
    if (lc < strlen(left)) {
      fmt_omap(dest, fmt_cnst);
      tmp_free(fmt);
      return;
    }
    fmt_nmap(-1, lbuf, fmt, left);

    strcpy(dest, lbuf);
    if (dp) {
      strcat(dest, ".");
      strcat(dest, rbuf);
    }
  }

  // sign in format
  if (sign) {                   // 24/6 Snoopy42 modifications
    char *e;

    e = strchr(dest, 'E');
    if (e) {                    // special treatment for E format 
      p = strchr(dest, '+');
      if (p && p < e) {          // the sign bust be before the E 
        *p = (sign > 0) ? '+' : '-';
      }
      p = strchr(dest, '-');
      if (p && p < e) {
        *p = (sign > 0) ? ' ' : '-';
      }
    } else {                      // no E format 
      p = strchr(dest, '+');
      if (p) {
        *p = (sign > 0) ? '+' : '-';
      }
      p = strchr(dest, '-');
      if (p) {
        *p = (sign > 0) ? ' ' : '-';
      }
    }
  }

  // cleanup
  tmp_free(fmt);
}
Пример #16
0
void v_resize_array(var_t *v, dword size)
#endif
{
  byte *prev;
  var_t *elem;
#if defined(OS_ADDR16)
  word i;
#else
  dword i;
#endif

  if (v->type == V_ARRAY) {
    if (size < 0) {
      err_evargerr();
      return;
    }

    if (size == 0) {
      v_free(v);
      v->type = V_ARRAY;
      v->v.a.size = 0;
      v->v.a.ptr = NULL;
      v->v.a.ubound[0] = v->v.a.lbound[0] = opt_base;
      v->v.a.maxdim = 1;
    } else if (v->v.a.size > size) {
      // resize down

      // free vars
      for (i = size; i < v->v.a.size; i++) {
        elem = (var_t *) (v->v.a.ptr + (sizeof(var_t) * i));
        v_free(elem);
      }

#if defined(OS_ADDR32)
      // do not resize array
      prev = NULL;
#else
      // resize & copy
      prev = v->v.a.ptr;
      v->v.a.ptr = tmp_alloc(size * sizeof(var_t));
      memcpy(v->v.a.ptr, prev, size * sizeof(var_t));
#endif
      // array data
      v->v.a.size = size;
      v->v.a.ubound[0] = v->v.a.lbound[0] + (size - 1);
      v->v.a.maxdim = 1;

      // 
      if (prev) {
        tmp_free(prev);
      }
    } else if (v->v.a.size < size) {
      // resize up

#if defined(OS_ADDR32)
      // if there is space do not resize 
      if (v->v.a.size == 0) {
        prev = v->v.a.ptr;
        v->v.a.ptr = tmp_alloc((size + ARR_ALLOC) * sizeof(var_t));
      } else {
        if (mem_handle_size(v->v.a.ptr) < size * sizeof(var_t)) {
          // resize & copy
          prev = v->v.a.ptr;
          v->v.a.ptr = tmp_alloc((size + ARR_ALLOC) * sizeof(var_t));
          if (v->v.a.size > 0)
            memcpy(v->v.a.ptr, prev, v->v.a.size * sizeof(var_t));
        } else
          prev = NULL;
      }
#else
      // resize & copy
      prev = v->v.a.ptr;
      v->v.a.ptr = tmp_alloc(size * sizeof(var_t));
      if (v->v.a.size > 0) {
        memcpy(v->v.a.ptr, prev, v->v.a.size * sizeof(var_t));
      }
#endif

      // init vars
      for (i = v->v.a.size; i < size; i++) {
        elem = (var_t *) (v->v.a.ptr + (sizeof(var_t) * i));
        v_init(elem);
      }

      // array data
      v->v.a.size = size;
      v->v.a.ubound[0] = v->v.a.lbound[0] + (size - 1);
      v->v.a.maxdim = 1;

      // 
      if (prev) {
        tmp_free(prev);
      }
    }
  } else {
    err_varisnotarray();
  }
}
Пример #17
0
XFontStruct *
x_font(x_display *xdpy, int font, int pixsize)
{
  char nm[128], *name;
  XFontStruct *f;
  if (tmp_fonts) tmp_free();

  if (font>=P_GUI_FONT || font<0 || pixsize<=0 || pixsize>180) {
    f = xdpy->font;

  } else {
    int siz, i, j, pass, *ip, *jp;
    for (pass=siz=0 ;; pass++) {
      ip = jp = 0;
      j = -1;
      i = xdpy->most_recent;
      while (i>=0) {
        if (!xdpy->cached[i].f) {
          /* handle interrupted unload operation */
          if (ip) *ip = -1;
          break;
        }
        if (xdpy->cached[i].font==font &&
            xdpy->cached[i].pixsize==pixsize) {
          if (ip) {
            /* CRITICAL section */
            *ip = xdpy->cached[i].next;
            xdpy->cached[i].next = xdpy->most_recent;
            xdpy->most_recent = i;
          }
          return xdpy->cached[i].f;
        }
        jp = ip;
        ip = &xdpy->cached[i].next;
        j = i;
        i = *ip;
      }
      if (pass) break;
      siz = x_substitute(xdpy, &font, &pixsize);
      if (font==P_GUI_FONT) return xdpy->font;
    }

    /* construct font name */
    name = xdpy->available[font].names[siz];
    if (!xdpy->available[font].sizes[siz]) {
      /* scalable, need to find specific instance */
      char *pnm = nm;
      int n = 7;
      while (n--) while ((*(pnm++)= *(name++))!='-');
      sprintf(pnm, "%d%n", pixsize, &n);
      strcpy(pnm+n, name);
      tmp_fonts = XListFonts(xdpy->dpy, nm, 4, &n);
      if (n<=0) return xdpy->font;  /* should never happen (X server bug) */
      strcpy(nm, tmp_fonts[0]);
      XFreeFontNames(tmp_fonts);
      tmp_free();
      name = nm;
    }

    /* should be able to load it */
    f = XLoadQueryFont(xdpy->dpy, name);
    if (!f) return xdpy->font;      /* should never happen (X server bug) */

    if (!xdpy->cached[0].f) {
      /* cache not yet full */
      for (j=0 ; j<N_FONT_CACHE-1 ; j++)
        if (xdpy->cached[j+1].f) break;
    } else {
      /* cache is full, need to unload one, j is least recent */
      XFontStruct *fold = xdpy->cached[j].f;
      xdpy->cached[j].f = 0;
      if (jp) *jp = -1;   /* jp pointed to j, now least recent */
      XFreeFont(xdpy->dpy, fold);
    }

    xdpy->cached[j].font = font;
    xdpy->cached[j].pixsize = pixsize;
    xdpy->cached[j].f = f;
    xdpy->cached[j].next = xdpy->most_recent;
    xdpy->most_recent = j;
  }

  if (p_signalling) p_abort();

  return f;
}