Example #1
0
static USHORT Process_Track(struct zfile *fi, struct zfile *fo, UCHAR *b1, UCHAR *b2, USHORT cmd, USHORT opt, int32_t dmsflags, struct zfile **extra){
	USHORT hcrc, dcrc, usum, number, pklen1, pklen2, unpklen, l;
	UCHAR cmode, flags;
	int32_t crcerr = 0;


	l = (USHORT)zfile_fread(b1,1,THLEN,fi);

	if (l != THLEN) {
		if (l==0)
			return DMS_FILE_END;
		else
			return ERR_SREAD;
	}

	/*  "TR" identifies a Track Header  */
	if ((b1[0] != 'T')||(b1[1] != 'R')) return ERR_NOTTRACK;

	/*  Track Header CRC  */
	hcrc = (USHORT)((b1[THLEN-2] << 8) | b1[THLEN-1]);

	if (dms_CreateCRC(b1,(ULONG)(THLEN-2)) != hcrc) return ERR_THCRC;

	number = (USHORT)((b1[2] << 8) | b1[3]);	/*  Number of track  */
	pklen1 = (USHORT)((b1[6] << 8) | b1[7]);	/*  Length of packed track data as in archive  */
	pklen2 = (USHORT)((b1[8] << 8) | b1[9]);	/*  Length of data after first unpacking  */
	unpklen = (USHORT)((b1[10] << 8) | b1[11]);	/*  Length of data after subsequent rle unpacking */
	flags = b1[12];		/*  control flags  */
	cmode = b1[13];		/*  compression mode used  */
	usum = (USHORT)((b1[14] << 8) | b1[15]);	/*  Track Data CheckSum AFTER unpacking  */
	dcrc = (USHORT)((b1[16] << 8) | b1[17]);	/*  Track Data CRC BEFORE unpacking  */

	if (dolog)
		write_log ("DMS: track=%d\n", number);

	if (dolog) {
		if (number==80)
			write_log (" FileID   ");
		else if (number==0xffff)
			write_log (" Banner   ");
		else if ((number==0) && (unpklen==1024))
			write_log (" FakeBB   ");
		else
			write_log ("   %2d     ",(short)number);

	    write_log ("%5d    %5d   %s  %04X  %04X  %04X    %0d\n", pklen1, unpklen, modes[cmode], usum, hcrc, dcrc, flags);
	}

	if ((pklen1 > TRACK_BUFFER_LEN) || (pklen2 >TRACK_BUFFER_LEN) || (unpklen > TRACK_BUFFER_LEN)) return ERR_BIGTRACK;

	if (zfile_fread(b1,1,(size_t)pklen1,fi) != pklen1) return ERR_SREAD;

	if (dms_CreateCRC(b1,(ULONG)pklen1) != dcrc) {
		log_error (number);
		crcerr = 1;
	}
	/*  track 80 is FILEID.DIZ, track 0xffff (-1) is Banner  */
	/*  and track 0 with 1024 bytes only is a fake boot block with more advertising */
	/*  FILE_ID.DIZ is never encrypted  */

	//if (pwd && (number!=80)) dms_decrypt(b1,pklen1);

	if ((cmd == CMD_UNPACK) && (number<80) && (unpklen>2048)) {
		memset(b2, 0, unpklen);
		if (!crcerr)
			Unpack_Track(b1, b2, pklen2, unpklen, cmode, flags, number, pklen1, usum, dmsflags & DMSFLAG_ENCRYPTED);
		if (number == 0 && zfile_ftell (fo) == 512 * 22) {
			// did we have another cylinder 0 already?
			uint8_t *p;
			zfile_fseek (fo, 0, SEEK_SET);
			p = xcalloc (uint8_t, 512 * 22);
			zfile_fread (p, 512 * 22, 1, fo);
			addextra("BigFakeBootBlock", extra, p, 512 * 22);
			xfree (p);
		}
		zfile_fseek (fo, number * 512 * 22 * ((dmsflags & DMSFLAG_HD) ? 2 : 1), SEEK_SET);
		if (zfile_fwrite(b2,1,(size_t)unpklen,fo) != unpklen)
			return ERR_CANTWRITE;
	} else if (number == 0 && unpklen == 1024) {
		memset(b2, 0, unpklen);
		if (!crcerr)
			Unpack_Track(b1, b2, pklen2, unpklen, cmode, flags, number, pklen1, usum, dmsflags & DMSFLAG_ENCRYPTED);
		addextra("FakeBootBlock", extra, b2, unpklen);
	}

	if (crcerr)
		return NO_PROBLEM;

	if (number == 0xffff && extra){
		Unpack_Track(b1, b2, pklen2, unpklen, cmode, flags, number, pklen1, usum, dmsflags & DMSFLAG_ENCRYPTED);
		addextra("Banner", extra, b2, unpklen);
		printbandiz(b2,unpklen);
	}

	if (number == 80 && extra) {
		Unpack_Track(b1, b2, pklen2, unpklen, cmode, flags, number, pklen1, usum, dmsflags & DMSFLAG_ENCRYPTED);
		addextra("FILEID.DIZ", extra, b2, unpklen);
		printbandiz(b2,unpklen);
	}

	return NO_PROBLEM;

}
Example #2
0
void build_problem(MPL *mpl)
{     STATEMENT *stmt;
      MEMBER *memb;
      VARIABLE *v;
      CONSTRAINT *c;
      FORMULA *t;
      int i, j;
      xassert(mpl->m == 0);
      xassert(mpl->n == 0);
      xassert(mpl->row == NULL);
      xassert(mpl->col == NULL);
      /* check that all elemental variables has zero column numbers */
      for (stmt = mpl->model; stmt != NULL; stmt = stmt->next)
      {  if (stmt->type == A_VARIABLE)
         {  v = stmt->u.var;
            for (memb = v->array->head; memb != NULL; memb = memb->next)
               xassert(memb->value.var->j == 0);
         }
      }
      /* assign row numbers to elemental constraints and objectives */
      for (stmt = mpl->model; stmt != NULL; stmt = stmt->next)
      {  if (stmt->type == A_CONSTRAINT)
         {  c = stmt->u.con;
            for (memb = c->array->head; memb != NULL; memb = memb->next)
            {  xassert(memb->value.con->i == 0);
               memb->value.con->i = ++mpl->m;
               /* walk through linear form and mark elemental variables,
                  which are referenced at least once */
               for (t = memb->value.con->form; t != NULL; t = t->next)
               {  xassert(t->var != NULL);
                  t->var->memb->value.var->j = -1;
               }
            }
         }
      }
      /* assign column numbers to marked elemental variables */
      for (stmt = mpl->model; stmt != NULL; stmt = stmt->next)
      {  if (stmt->type == A_VARIABLE)
         {  v = stmt->u.var;
            for (memb = v->array->head; memb != NULL; memb = memb->next)
               if (memb->value.var->j != 0) memb->value.var->j =
                  ++mpl->n;
         }
      }
      /* build list of rows */
      mpl->row = xcalloc(1+mpl->m, sizeof(ELEMCON *));
      for (i = 1; i <= mpl->m; i++) mpl->row[i] = NULL;
      for (stmt = mpl->model; stmt != NULL; stmt = stmt->next)
      {  if (stmt->type == A_CONSTRAINT)
         {  c = stmt->u.con;
            for (memb = c->array->head; memb != NULL; memb = memb->next)
            {  i = memb->value.con->i;
               xassert(1 <= i && i <= mpl->m);
               xassert(mpl->row[i] == NULL);
               mpl->row[i] = memb->value.con;
            }
         }
      }
      for (i = 1; i <= mpl->m; i++) xassert(mpl->row[i] != NULL);
      /* build list of columns */
      mpl->col = xcalloc(1+mpl->n, sizeof(ELEMVAR *));
      for (j = 1; j <= mpl->n; j++) mpl->col[j] = NULL;
      for (stmt = mpl->model; stmt != NULL; stmt = stmt->next)
      {  if (stmt->type == A_VARIABLE)
         {  v = stmt->u.var;
            for (memb = v->array->head; memb != NULL; memb = memb->next)
            {  j = memb->value.var->j;
               if (j == 0) continue;
               xassert(1 <= j && j <= mpl->n);
               xassert(mpl->col[j] == NULL);
               mpl->col[j] = memb->value.var;
            }
         }
      }
      for (j = 1; j <= mpl->n; j++) xassert(mpl->col[j] != NULL);
      return;
}
Example #3
0
MPL *mpl_initialize(void)
{     MPL *mpl;
      mpl = xmalloc(sizeof(MPL));
      /* scanning segment */
      mpl->line = 0;
      mpl->c = 0;
      mpl->token = 0;
      mpl->imlen = 0;
      mpl->image = xcalloc(MAX_LENGTH+1, sizeof(char));
      mpl->image[0] = '\0';
      mpl->value = 0.0;
      mpl->b_token = 0;
      mpl->b_imlen = 0;
      mpl->b_image = xcalloc(MAX_LENGTH+1, sizeof(char));
      mpl->b_image[0] = '\0';
      mpl->b_value = 0.0;
      mpl->f_dots = 0;
      mpl->f_scan = 0;
      mpl->f_token = 0;
      mpl->f_imlen = 0;
      mpl->f_image = xcalloc(MAX_LENGTH+1, sizeof(char));
      mpl->f_image[0] = '\0';
      mpl->f_value = 0.0;
      mpl->context = xcalloc(CONTEXT_SIZE, sizeof(char));
      memset(mpl->context, ' ', CONTEXT_SIZE);
      mpl->c_ptr = 0;
      mpl->flag_d = 0;
      /* translating segment */
      mpl->pool = dmp_create_poolx(0);
      mpl->tree = avl_create_tree(avl_strcmp, NULL);
      mpl->model = NULL;
      mpl->flag_x = 0;
      mpl->as_within = 0;
      mpl->as_in = 0;
      mpl->as_binary = 0;
      mpl->flag_s = 0;
      /* common segment */
      mpl->strings = dmp_create_poolx(sizeof(STRING));
      mpl->symbols = dmp_create_poolx(sizeof(SYMBOL));
      mpl->tuples = dmp_create_poolx(sizeof(TUPLE));
      mpl->arrays = dmp_create_poolx(sizeof(ARRAY));
      mpl->members = dmp_create_poolx(sizeof(MEMBER));
      mpl->elemvars = dmp_create_poolx(sizeof(ELEMVAR));
      mpl->formulae = dmp_create_poolx(sizeof(FORMULA));
      mpl->elemcons = dmp_create_poolx(sizeof(ELEMCON));
      mpl->a_list = NULL;
      mpl->sym_buf = xcalloc(255+1, sizeof(char));
      mpl->sym_buf[0] = '\0';
      mpl->tup_buf = xcalloc(255+1, sizeof(char));
      mpl->tup_buf[0] = '\0';
      /* generating/postsolving segment */
      mpl->rand = rng_create_rand();
      mpl->flag_p = 0;
      mpl->stmt = NULL;
#if 1 /* 11/II-2008 */
      mpl->dca = NULL;
#endif
      mpl->m = 0;
      mpl->n = 0;
      mpl->row = NULL;
      mpl->col = NULL;
      /* input/output segment */
      mpl->in_fp = NULL;
      mpl->in_file = NULL;
      mpl->out_fp = NULL;
      mpl->out_file = NULL;
      mpl->prt_fp = NULL;
      mpl->prt_file = NULL;
      /* solver interface segment */
      if (setjmp(mpl->jump)) xassert(mpl != mpl);
      mpl->phase = 0;
      mpl->mod_file = NULL;
      mpl->mpl_buf = xcalloc(255+1, sizeof(char));
      mpl->mpl_buf[0] = '\0';
      return mpl;
}
Example #4
0
void lpx_eval_b_prim(LPX *lp, double row_prim[], double col_prim[])
{     int i, j, k, m, n, stat, len, *ind;
      double xN, *NxN, *xB, *val;
      if (!lpx_is_b_avail(lp))
         xfault("lpx_eval_b_prim: LP basis is not available\n");
      m = lpx_get_num_rows(lp);
      n = lpx_get_num_cols(lp);
      /* store values of non-basic auxiliary and structural variables
         and compute the right-hand side vector (-N*xN) */
      NxN = xcalloc(1+m, sizeof(double));
      for (i = 1; i <= m; i++) NxN[i] = 0.0;
      /* walk through auxiliary variables */
      for (i = 1; i <= m; i++)
      {  /* obtain status of i-th auxiliary variable */
         stat = lpx_get_row_stat(lp, i);
         /* if it is basic, skip it */
         if (stat == LPX_BS) continue;
         /* i-th auxiliary variable is non-basic; get its value */
         switch (stat)
         {  case LPX_NL: xN = lpx_get_row_lb(lp, i); break;
            case LPX_NU: xN = lpx_get_row_ub(lp, i); break;
            case LPX_NF: xN = 0.0; break;
            case LPX_NS: xN = lpx_get_row_lb(lp, i); break;
            default: xassert(lp != lp);
         }
         /* store the value of non-basic auxiliary variable */
         row_prim[i] = xN;
         /* and add corresponding term to the right-hand side vector */
         NxN[i] -= xN;
      }
      /* walk through structural variables */
      ind = xcalloc(1+m, sizeof(int));
      val = xcalloc(1+m, sizeof(double));
      for (j = 1; j <= n; j++)
      {  /* obtain status of j-th structural variable */
         stat = lpx_get_col_stat(lp, j);
         /* if it basic, skip it */
         if (stat == LPX_BS) continue;
         /* j-th structural variable is non-basic; get its value */
         switch (stat)
         {  case LPX_NL: xN = lpx_get_col_lb(lp, j); break;
            case LPX_NU: xN = lpx_get_col_ub(lp, j); break;
            case LPX_NF: xN = 0.0; break;
            case LPX_NS: xN = lpx_get_col_lb(lp, j); break;
            default: xassert(lp != lp);
         }
         /* store the value of non-basic structural variable */
         col_prim[j] = xN;
         /* and add corresponding term to the right-hand side vector */
         if (xN != 0.0)
         {  len = lpx_get_mat_col(lp, j, ind, val);
            for (k = 1; k <= len; k++) NxN[ind[k]] += val[k] * xN;
         }
      }
      xfree(ind);
      xfree(val);
      /* solve the system B*xB = (-N*xN) to compute the vector xB */
      xB = NxN, lpx_ftran(lp, xB);
      /* store values of basic auxiliary and structural variables */
      for (i = 1; i <= m; i++)
      {  k = lpx_get_b_info(lp, i);
         xassert(1 <= k && k <= m+n);
         if (k <= m)
            row_prim[k] = xB[i];
         else
            col_prim[k-m] = xB[i];
      }
      xfree(NxN);
      return;
}
Example #5
0
static struct discovery *discover_refs(const char *service, int for_push)
{
	struct strbuf exp = STRBUF_INIT;
	struct strbuf type = STRBUF_INIT;
	struct strbuf charset = STRBUF_INIT;
	struct strbuf buffer = STRBUF_INIT;
	struct strbuf refs_url = STRBUF_INIT;
	struct strbuf effective_url = STRBUF_INIT;
	struct strbuf protocol_header = STRBUF_INIT;
	struct string_list extra_headers = STRING_LIST_INIT_DUP;
	struct discovery *last = last_discovery;
	int http_ret, maybe_smart = 0;
	struct http_get_options http_options;
	enum protocol_version version = get_protocol_version_config();

	if (last && !strcmp(service, last->service))
		return last;
	free_discovery(last);

	strbuf_addf(&refs_url, "%sinfo/refs", url.buf);
	if ((starts_with(url.buf, "http://") || starts_with(url.buf, "https://")) &&
	     git_env_bool("GIT_SMART_HTTP", 1)) {
		maybe_smart = 1;
		if (!strchr(url.buf, '?'))
			strbuf_addch(&refs_url, '?');
		else
			strbuf_addch(&refs_url, '&');
		strbuf_addf(&refs_url, "service=%s", service);
	}

	/*
	 * NEEDSWORK: If we are trying to use protocol v2 and we are planning
	 * to perform a push, then fallback to v0 since the client doesn't know
	 * how to push yet using v2.
	 */
	if (version == protocol_v2 && !strcmp("git-receive-pack", service))
		version = protocol_v0;

	/* Add the extra Git-Protocol header */
	if (get_protocol_http_header(version, &protocol_header))
		string_list_append(&extra_headers, protocol_header.buf);

	memset(&http_options, 0, sizeof(http_options));
	http_options.content_type = &type;
	http_options.charset = &charset;
	http_options.effective_url = &effective_url;
	http_options.base_url = &url;
	http_options.extra_headers = &extra_headers;
	http_options.initial_request = 1;
	http_options.no_cache = 1;
	http_options.keep_error = 1;

	http_ret = http_get_strbuf(refs_url.buf, &buffer, &http_options);
	switch (http_ret) {
	case HTTP_OK:
		break;
	case HTTP_MISSING_TARGET:
		show_http_message(&type, &charset, &buffer);
		die("repository '%s' not found", url.buf);
	case HTTP_NOAUTH:
		show_http_message(&type, &charset, &buffer);
		die("Authentication failed for '%s'", url.buf);
	default:
		show_http_message(&type, &charset, &buffer);
		die("unable to access '%s': %s", url.buf, curl_errorstr);
	}

	if (options.verbosity && !starts_with(refs_url.buf, url.buf))
		warning(_("redirecting to %s"), url.buf);

	last= xcalloc(1, sizeof(*last_discovery));
	last->service = xstrdup(service);
	last->buf_alloc = strbuf_detach(&buffer, &last->len);
	last->buf = last->buf_alloc;

	strbuf_addf(&exp, "application/x-%s-advertisement", service);
	if (maybe_smart &&
	    (5 <= last->len && last->buf[4] == '#') &&
	    !strbuf_cmp(&exp, &type)) {
		char *line;

		/*
		 * smart HTTP response; validate that the service
		 * pkt-line matches our request.
		 */
		line = packet_read_line_buf(&last->buf, &last->len, NULL);
		if (!line)
			die("invalid server response; expected service, got flush packet");

		strbuf_reset(&exp);
		strbuf_addf(&exp, "# service=%s", service);
		if (strcmp(line, exp.buf))
			die("invalid server response; got '%s'", line);
		strbuf_release(&exp);

		/* The header can include additional metadata lines, up
		 * until a packet flush marker.  Ignore these now, but
		 * in the future we might start to scan them.
		 */
		while (packet_read_line_buf(&last->buf, &last->len, NULL))
			;

		last->proto_git = 1;
	} else if (maybe_smart &&
		   last->len > 5 && starts_with(last->buf + 4, "version 2")) {
		last->proto_git = 1;
	}

	if (last->proto_git)
		last->refs = parse_git_refs(last, for_push);
	else
		last->refs = parse_info_refs(last);

	strbuf_release(&refs_url);
	strbuf_release(&exp);
	strbuf_release(&type);
	strbuf_release(&charset);
	strbuf_release(&effective_url);
	strbuf_release(&buffer);
	strbuf_release(&protocol_header);
	string_list_clear(&extra_headers, 0);
	last_discovery = last;
	return last;
}
Example #6
0
int lpx_warm_up(LPX *lp)
{     int m, n, j, k, ret, type, stat, p_stat, d_stat;
      double lb, ub, prim, dual, tol_bnd, tol_dj, dir;
      double *row_prim, *row_dual, *col_prim, *col_dual, sum;
      m = lpx_get_num_rows(lp);
      n = lpx_get_num_cols(lp);
      /* reinvert the basis matrix, if necessary */
      if (lpx_is_b_avail(lp))
         ret = LPX_E_OK;
      else
      {  if (m == 0 || n == 0)
         {  ret = LPX_E_EMPTY;
            goto done;
         }
#if 0
         ret = lpx_invert(lp);
         switch (ret)
         {  case 0:
               ret = LPX_E_OK;
               break;
            case 1:
            case 2:
               ret = LPX_E_SING;
               goto done;
            case 3:
               ret = LPX_E_BADB;
               goto done;
            default:
               xassert(ret != ret);
         }
#else
         switch (glp_factorize(lp))
         {  case 0:
               ret = LPX_E_OK;
               break;
            case GLP_EBADB:
               ret = LPX_E_BADB;
               goto done;
            case GLP_ESING:
            case GLP_ECOND:
               ret = LPX_E_SING;
               goto done;
            default:
               xassert(lp != lp);
         }
#endif
      }
      /* allocate working arrays */
      row_prim = xcalloc(1+m, sizeof(double));
      row_dual = xcalloc(1+m, sizeof(double));
      col_prim = xcalloc(1+n, sizeof(double));
      col_dual = xcalloc(1+n, sizeof(double));
      /* compute primal basic solution components */
      lpx_eval_b_prim(lp, row_prim, col_prim);
      /* determine primal status of basic solution */
      tol_bnd = 3.0 * lpx_get_real_parm(lp, LPX_K_TOLBND);
      p_stat = LPX_P_FEAS;
      for (k = 1; k <= m+n; k++)
      {  if (k <= m)
         {  type = lpx_get_row_type(lp, k);
            lb = lpx_get_row_lb(lp, k);
            ub = lpx_get_row_ub(lp, k);
            prim = row_prim[k];
         }
         else
         {  type = lpx_get_col_type(lp, k-m);
            lb = lpx_get_col_lb(lp, k-m);
            ub = lpx_get_col_ub(lp, k-m);
            prim = col_prim[k-m];
         }
         if (type == LPX_LO || type == LPX_DB || type == LPX_FX)
         {  /* variable x[k] has lower bound */
            if (prim < lb - tol_bnd * (1.0 + fabs(lb)))
            {  p_stat = LPX_P_INFEAS;
               break;
            }
         }
         if (type == LPX_UP || type == LPX_DB || type == LPX_FX)
         {  /* variable x[k] has upper bound */
            if (prim > ub + tol_bnd * (1.0 + fabs(ub)))
            {  p_stat = LPX_P_INFEAS;
               break;
            }
         }
      }
      /* compute dual basic solution components */
      lpx_eval_b_dual(lp, row_dual, col_dual);
      /* determine dual status of basic solution */
      tol_dj = 3.0 * lpx_get_real_parm(lp, LPX_K_TOLDJ);
      dir = (lpx_get_obj_dir(lp) == LPX_MIN ? +1.0 : -1.0);
      d_stat = LPX_D_FEAS;
      for (k = 1; k <= m+n; k++)
      {  if (k <= m)
         {  stat = lpx_get_row_stat(lp, k);
            dual = row_dual[k];
         }
         else
         {  stat = lpx_get_col_stat(lp, k-m);
            dual = col_dual[k-m];
         }
         if (stat == LPX_BS || stat == LPX_NL || stat == LPX_NF)
         {  /* reduced cost of x[k] must be non-negative (minimization)
               or non-positive (maximization) */
            if (dir * dual < - tol_dj)
            {  d_stat = LPX_D_INFEAS;
               break;
            }
         }
         if (stat == LPX_BS || stat == LPX_NU || stat == LPX_NF)
         {  /* reduced cost of x[k] must be non-positive (minimization)
               or non-negative (maximization) */
            if (dir * dual > + tol_dj)
            {  d_stat = LPX_D_INFEAS;
               break;
            }
         }
      }
      /* store basic solution components */
      p_stat = p_stat - LPX_P_UNDEF + GLP_UNDEF;
      d_stat = d_stat - LPX_D_UNDEF + GLP_UNDEF;
      sum = lpx_get_obj_coef(lp, 0);
      for (j = 1; j <= n; j++)
         sum += lpx_get_obj_coef(lp, j) * col_prim[j];
      glp_put_solution(lp, 0, &p_stat, &d_stat, &sum,
         NULL, row_prim, row_dual, NULL, col_prim, col_dual);
      xassert(lpx_is_b_avail(lp));
      /* free working arrays */
      xfree(row_prim);
      xfree(row_dual);
      xfree(col_prim);
      xfree(col_dual);
done: /* return to the calling program */
      return ret;
}
Example #7
0
int lpx_transform_row(LPX *lp, int len, int ind[], double val[])
{     int i, j, k, m, n, t, lll, *iii;
      double alfa, *a, *aB, *rho, *vvv;
      if (!lpx_is_b_avail(lp))
         xfault("lpx_transform_row: LP basis is not available\n");
      m = lpx_get_num_rows(lp);
      n = lpx_get_num_cols(lp);
      /* unpack the row to be transformed to the array a */
      a = xcalloc(1+n, sizeof(double));
      for (j = 1; j <= n; j++) a[j] = 0.0;
      if (!(0 <= len && len <= n))
         xfault("lpx_transform_row: len = %d; invalid row length\n",
            len);
      for (t = 1; t <= len; t++)
      {  j = ind[t];
         if (!(1 <= j && j <= n))
            xfault("lpx_transform_row: ind[%d] = %d; column index out o"
               "f range\n", t, j);
         if (val[t] == 0.0)
            xfault("lpx_transform_row: val[%d] = 0; zero coefficient no"
               "t allowed\n", t);
         if (a[j] != 0.0)
            xfault("lpx_transform_row: ind[%d] = %d; duplicate column i"
               "ndices not allowed\n", t, j);
         a[j] = val[t];
      }
      /* construct the vector aB */
      aB = xcalloc(1+m, sizeof(double));
      for (i = 1; i <= m; i++)
      {  k = lpx_get_b_info(lp, i);
         /* xB[i] is k-th original variable */
         xassert(1 <= k && k <= m+n);
         aB[i] = (k <= m ? 0.0 : a[k-m]);
      }
      /* solve the system B'*rho = aB to compute the vector rho */
      rho = aB, lpx_btran(lp, rho);
      /* compute coefficients at non-basic auxiliary variables */
      len = 0;
      for (i = 1; i <= m; i++)
      {  if (lpx_get_row_stat(lp, i) != LPX_BS)
         {  alfa = - rho[i];
            if (alfa != 0.0)
            {  len++;
               ind[len] = i;
               val[len] = alfa;
            }
         }
      }
      /* compute coefficients at non-basic structural variables */
      iii = xcalloc(1+m, sizeof(int));
      vvv = xcalloc(1+m, sizeof(double));
      for (j = 1; j <= n; j++)
      {  if (lpx_get_col_stat(lp, j) != LPX_BS)
         {  alfa = a[j];
            lll = lpx_get_mat_col(lp, j, iii, vvv);
            for (t = 1; t <= lll; t++) alfa += vvv[t] * rho[iii[t]];
            if (alfa != 0.0)
            {  len++;
               ind[len] = m+j;
               val[len] = alfa;
            }
         }
      }
      xassert(len <= n);
      xfree(iii);
      xfree(vvv);
      xfree(aB);
      xfree(a);
      return len;
}
Example #8
0
/*ARGSUSED*/
void
dolist(Char **v, struct command *c)
{
    Char **globbed;
    int     i, k;
    struct stat st;

    USE(c);
    if (*++v == NULL) {
	struct Strbuf word = Strbuf_INIT;

	Strbuf_terminate(&word);
	cleanup_push(&word, Strbuf_cleanup);
	(void) t_search(&word, LIST, TW_ZERO, 0, STRNULL, 0);
	cleanup_until(&word);
	return;
    }
    v = glob_all_or_error(v);
    globbed = v;
    cleanup_push(globbed, blk_cleanup);
    for (k = 0; v[k] != NULL && v[k][0] != '-'; k++)
	continue;
    if (v[k]) {
	/*
	 * We cannot process a flag therefore we let ls do it right.
	 */
	Char *lspath;
	struct command *t;
	struct wordent cmd, *nextword, *lastword;
	Char   *cp;
	struct varent *vp;

	if (setintr) {
	    pintr_disabled++;
	    cleanup_push(&pintr_disabled, disabled_cleanup);
	}
	if (seterr) {
	    xfree(seterr);
	    seterr = NULL;
	}

	lspath = STRls;
	STRmCF[1] = 'C';
	STRmCF[3] = '\0';
	/* Look at listflags, to add -A to the flags, to get a path
	   of ls if necessary */
	if ((vp = adrof(STRlistflags)) != NULL && vp->vec != NULL &&
	    vp->vec[0] != STRNULL) {
	    if (vp->vec[1] != NULL && vp->vec[1][0] != '\0')
		lspath = vp->vec[1];
	    for (cp = vp->vec[0]; *cp; cp++)
		switch (*cp) {
		case 'x':
		    STRmCF[1] = 'x';
		    break;
		case 'a':
		    STRmCF[3] = 'a';
		    break;
		case 'A':
		    STRmCF[3] = 'A';
		    break;
		default:
		    break;
		}
	}

	cmd.word = STRNULL;
	lastword = &cmd;
	nextword = xcalloc(1, sizeof cmd);
	nextword->word = Strsave(lspath);
	lastword->next = nextword;
	nextword->prev = lastword;
	lastword = nextword;
	nextword = xcalloc(1, sizeof cmd);
	nextword->word = Strsave(STRmCF);
	lastword->next = nextword;
	nextword->prev = lastword;
#if defined(KANJI) && defined(SHORT_STRINGS) && defined(DSPMBYTE)
	if (dspmbyte_ls) {
	    lastword = nextword;
	    nextword = xcalloc(1, sizeof cmd);
	    nextword->word = Strsave(STRmmliteral);
	    lastword->next = nextword;
	    nextword->prev = lastword;
	}
#endif
#ifdef COLOR_LS_F
	if (color_context_ls) {
	    lastword = nextword;
	    nextword = xcalloc(1, sizeof cmd);
	    nextword->word = Strsave(STRmmcolormauto);
	    lastword->next = nextword;
	    nextword->prev = lastword;
	}
#endif /* COLOR_LS_F */
	lastword = nextword;
	for (cp = *v; cp; cp = *++v) {
	    nextword = xcalloc(1, sizeof cmd);
	    nextword->word = quote(Strsave(cp));
	    lastword->next = nextword;
	    nextword->prev = lastword;
	    lastword = nextword;
	}
	lastword->next = &cmd;
	cmd.prev = lastword;
	cleanup_push(&cmd, lex_cleanup);

	/* build a syntax tree for the command. */
	t = syntax(cmd.next, &cmd, 0);
	cleanup_push(t, syntax_cleanup);
	if (seterr)
	    stderror(ERR_OLD);
	/* expand aliases like process() does */
	/* alias(&cmd); */
	/* execute the parse tree. */
	execute(t, tpgrp > 0 ? tpgrp : -1, NULL, NULL, FALSE);
	/* done. free the lex list and parse tree. */
	cleanup_until(&cmd);
	if (setintr)
	    cleanup_until(&pintr_disabled);
    }
    else {
	Char   *dp, *tmp;
	struct Strbuf buf = Strbuf_INIT;

	cleanup_push(&buf, Strbuf_cleanup);
	for (k = 0, i = 0; v[k] != NULL; k++) {
	    tmp = dnormalize(v[k], symlinks == SYM_IGNORE);
	    cleanup_push(tmp, xfree);
	    dp = Strend(tmp) - 1;
	    if (*dp == '/' && dp != tmp)
#ifdef apollo
		if (dp != &tmp[1])
#endif /* apollo */
		*dp = '\0';
	    if (stat(short2str(tmp), &st) == -1) {
		int err;

		err = errno;
		if (k != i) {
		    if (i != 0)
			xputchar('\n');
		    print_by_column(STRNULL, &v[i], k - i, FALSE);
		}
		xprintf("%S: %s.\n", tmp, strerror(err));
		i = k + 1;
	    }
	    else if (S_ISDIR(st.st_mode)) {
		Char   *cp;

		if (k != i) {
		    if (i != 0)
			xputchar('\n');
		    print_by_column(STRNULL, &v[i], k - i, FALSE);
		}
		if (k != 0 && v[1] != NULL)
		    xputchar('\n');
		xprintf("%S:\n", tmp);
		buf.len = 0;
		for (cp = tmp; *cp; cp++)
		    Strbuf_append1(&buf, (*cp | QUOTE));
		Strbuf_terminate(&buf);
		dp = &buf.s[buf.len - 1];
		if (
#ifdef WINNT_NATIVE
		    (*dp != (Char) (':' | QUOTE)) &&
#endif /* WINNT_NATIVE */
		    (*dp != (Char) ('/' | QUOTE))) {
		    Strbuf_append1(&buf, '/');
		    Strbuf_terminate(&buf);
		} else 
		    *dp &= TRIM;
		(void) t_search(&buf, LIST, TW_ZERO, 0, STRNULL, 0);
		i = k + 1;
	    }
	    cleanup_until(tmp);
	}
	cleanup_until(&buf);
	if (k != i) {
	    if (i != 0)
		xputchar('\n');
	    print_by_column(STRNULL, &v[i], k - i, FALSE);
	}
    }

    cleanup_until(globbed);
}
Example #9
0
/*
 * Karl Kleinpaste, 21oct1983.
 * Set up a one-word alias command, for use for special things.
 * This code is based on the mainline of process().
 */
void
aliasrun(int cnt, Char *s1, Char *s2)
{
    struct wordent w, *new1, *new2;	/* for holding alias name */
    struct command *t = NULL;
    jmp_buf_t osetexit;
    int status;
    size_t omark;

    getexit(osetexit);
    if (seterr) {
	xfree(seterr);
	seterr = NULL;	/* don't repeatedly print err msg. */
    }
    w.word = STRNULL;
    new1 = xcalloc(1, sizeof w);
    new1->word = Strsave(s1);
    if (cnt == 1) {
	/* build a lex list with one word. */
	w.next = w.prev = new1;
	new1->next = new1->prev = &w;
    }
    else {
	/* build a lex list with two words. */
	new2 = xcalloc(1, sizeof w);
	new2->word = Strsave(s2);
	w.next = new2->prev = new1;
	new1->next = w.prev = new2;
	new1->prev = new2->next = &w;
    }
    cleanup_push(&w, lex_cleanup);

    /* Save the old status */
    status = getn(varval(STRstatus));

    /* expand aliases like process() does. */
    alias(&w);
    /* build a syntax tree for the command. */
    t = syntax(w.next, &w, 0);
    cleanup_push(t, syntax_cleanup);
    if (seterr)
	stderror(ERR_OLD);

    psavejob();
    cleanup_push(&cnt, psavejob_cleanup); /* cnt is used only as a marker */

    /* catch any errors here */
    omark = cleanup_push_mark();
    if (setexit() == 0)
	/* execute the parse tree. */
	/*
	 * From: Michael Schroeder <*****@*****.**>
	 * was execute(t, tpgrp);
	 */
	execute(t, tpgrp > 0 ? tpgrp : -1, NULL, NULL, TRUE);
    /* reset the error catcher to the old place */
    cleanup_pop_mark(omark);
    resexit(osetexit);
    if (haderr) {
	haderr = 0;
	/*
	 * Either precmd, or cwdcmd, or periodic had an error. Call it again so
	 * that it is removed
	 */
	if (precmd_active)
	    precmd();
	if (postcmd_active)
	    postcmd();
#ifdef notdef
	/*
	 * XXX: On the other hand, just interrupting them causes an error too.
	 * So if we hit ^C in the middle of cwdcmd or periodic the alias gets
	 * removed. We don't want that. Note that we want to remove precmd
	 * though, cause that could lead into an infinite loop. This should be
	 * fixed correctly, but then haderr should give us the whole exit
	 * status not just true or false.
	 */
	else if (cwdcmd_active)
	    cwd_cmd();
	else if (beepcmd_active)
	    beep_cmd();
	else if (periodic_active)
	    period_cmd();
#endif /* notdef */
    }
    cleanup_until(&w);
    pendjob();
    /* Restore status */
    setv(STRstatus, putn((tcsh_number_t)status), VAR_READWRITE);
}
Example #10
0
/* The actual "aliasing" of for backgrounds() is done here
   with the aid of insert_we().   */
static void
insert(struct wordent *pl, int file_args)
{
    struct wordent *now, *last;
    Char   *cmd, *bcmd, *cp1, *cp2;
    size_t cmd_len;
    Char   *upause = STRunderpause;
    size_t p_len = Strlen(upause);

    cmd_len = Strlen(pl->word);
    cmd = xcalloc(1, (cmd_len + 1) * sizeof(Char));
    (void) Strcpy(cmd, pl->word);
/* Do insertions at beginning, first replace command word */

    if (file_args) {
	now = pl;
	xfree(now->word);
	now->word = xcalloc(1, 5 * sizeof(Char));
	(void) Strcpy(now->word, STRecho);

	now = xcalloc(1, sizeof(struct wordent));
	now->word = xcalloc(1, 6 * sizeof(Char));
	(void) Strcpy(now->word, STRbackqpwd);
	insert_we(now, pl);

	for (last = now; *last->word != '\n' && *last->word != ';';
	     last = last->next)
	    continue;

	now = xcalloc(1, sizeof(struct wordent));
	now->word = xcalloc(1, 2 * sizeof(Char));
	(void) Strcpy(now->word, STRgt);
	insert_we(now, last->prev);

	now = xcalloc(1, sizeof(struct wordent));
	now->word = xcalloc(1, 2 * sizeof(Char));
	(void) Strcpy(now->word, STRbang);
	insert_we(now, last->prev);

	now = xcalloc(1, sizeof(struct wordent));
	now->word = xcalloc(1, (cmd_len + p_len + 4) * sizeof(Char));
	cp1 = now->word;
	cp2 = cmd;
	*cp1++ = '~';
	*cp1++ = '/';
	*cp1++ = '.';
	while ((*cp1++ = *cp2++) != '\0')
	    continue;
	cp1--;
	cp2 = upause;
	while ((*cp1++ = *cp2++) != '\0')
	    continue;
	insert_we(now, last->prev);

	now = xcalloc(1, sizeof(struct wordent));
	now->word = xcalloc(1, 2 * sizeof(Char));
	(void) Strcpy(now->word, STRsemi);
	insert_we(now, last->prev);
	bcmd = xcalloc(1, (cmd_len + 2) * sizeof(Char));
	*bcmd = '%';
	Strcpy(bcmd + 1, cmd);
	now = xcalloc(1, sizeof(struct wordent));
	now->word = bcmd;
	insert_we(now, last->prev);
    }
    else {
	struct wordent *del;

	now = pl;
	xfree(now->word);
	now->word = xcalloc(1, (cmd_len + 2) * sizeof(Char));
	*now->word = '%';
	Strcpy(now->word + 1, cmd);
	for (now = now->next;
	     *now->word != '\n' && *now->word != ';' && now != pl;) {
	    now->prev->next = now->next;
	    now->next->prev = now->prev;
	    xfree(now->word);
	    del = now;
	    now = now->next;
	    xfree(del);
	}
    }
}
Example #11
0
File: grep.c Project: adityalnx/git
int cmd_grep(int argc, const char **argv, const char *prefix)
{
	int hit = 0;
	int cached = 0;
	int seen_dashdash = 0;
	int external_grep_allowed__ignored;
	const char *show_in_pager = NULL, *default_pager = "dummy";
	struct grep_opt opt;
	struct object_array list = OBJECT_ARRAY_INIT;
	const char **paths = NULL;
	struct string_list path_list = STRING_LIST_INIT_NODUP;
	int i;
	int dummy;
	int use_index = 1;
	struct option options[] = {
		OPT_BOOLEAN(0, "cached", &cached,
			"search in index instead of in the work tree"),
		OPT_BOOLEAN(0, "index", &use_index,
			"--no-index finds in contents not managed by git"),
		OPT_GROUP(""),
		OPT_BOOLEAN('v', "invert-match", &opt.invert,
			"show non-matching lines"),
		OPT_BOOLEAN('i', "ignore-case", &opt.ignore_case,
			"case insensitive matching"),
		OPT_BOOLEAN('w', "word-regexp", &opt.word_regexp,
			"match patterns only at word boundaries"),
		OPT_SET_INT('a', "text", &opt.binary,
			"process binary files as text", GREP_BINARY_TEXT),
		OPT_SET_INT('I', NULL, &opt.binary,
			"don't match patterns in binary files",
			GREP_BINARY_NOMATCH),
		{ OPTION_INTEGER, 0, "max-depth", &opt.max_depth, "depth",
			"descend at most <depth> levels", PARSE_OPT_NONEG,
			NULL, 1 },
		OPT_GROUP(""),
		OPT_BIT('E', "extended-regexp", &opt.regflags,
			"use extended POSIX regular expressions", REG_EXTENDED),
		OPT_NEGBIT('G', "basic-regexp", &opt.regflags,
			"use basic POSIX regular expressions (default)",
			REG_EXTENDED),
		OPT_BOOLEAN('F', "fixed-strings", &opt.fixed,
			"interpret patterns as fixed strings"),
		OPT_GROUP(""),
		OPT_BOOLEAN('n', NULL, &opt.linenum, "show line numbers"),
		OPT_NEGBIT('h', NULL, &opt.pathname, "don't show filenames", 1),
		OPT_BIT('H', NULL, &opt.pathname, "show filenames", 1),
		OPT_NEGBIT(0, "full-name", &opt.relative,
			"show filenames relative to top directory", 1),
		OPT_BOOLEAN('l', "files-with-matches", &opt.name_only,
			"show only filenames instead of matching lines"),
		OPT_BOOLEAN(0, "name-only", &opt.name_only,
			"synonym for --files-with-matches"),
		OPT_BOOLEAN('L', "files-without-match",
			&opt.unmatch_name_only,
			"show only the names of files without match"),
		OPT_BOOLEAN('z', "null", &opt.null_following_name,
			"print NUL after filenames"),
		OPT_BOOLEAN('c', "count", &opt.count,
			"show the number of matches instead of matching lines"),
		OPT__COLOR(&opt.color, "highlight matches"),
		OPT_GROUP(""),
		OPT_CALLBACK('C', NULL, &opt, "n",
			"show <n> context lines before and after matches",
			context_callback),
		OPT_INTEGER('B', NULL, &opt.pre_context,
			"show <n> context lines before matches"),
		OPT_INTEGER('A', NULL, &opt.post_context,
			"show <n> context lines after matches"),
		OPT_NUMBER_CALLBACK(&opt, "shortcut for -C NUM",
			context_callback),
		OPT_BOOLEAN('p', "show-function", &opt.funcname,
			"show a line with the function name before matches"),
		OPT_GROUP(""),
		OPT_CALLBACK('f', NULL, &opt, "file",
			"read patterns from file", file_callback),
		{ OPTION_CALLBACK, 'e', NULL, &opt, "pattern",
			"match <pattern>", PARSE_OPT_NONEG, pattern_callback },
		{ OPTION_CALLBACK, 0, "and", &opt, NULL,
		  "combine patterns specified with -e",
		  PARSE_OPT_NOARG | PARSE_OPT_NONEG, and_callback },
		OPT_BOOLEAN(0, "or", &dummy, ""),
		{ OPTION_CALLBACK, 0, "not", &opt, NULL, "",
		  PARSE_OPT_NOARG | PARSE_OPT_NONEG, not_callback },
		{ OPTION_CALLBACK, '(', NULL, &opt, NULL, "",
		  PARSE_OPT_NOARG | PARSE_OPT_NONEG | PARSE_OPT_NODASH,
		  open_callback },
		{ OPTION_CALLBACK, ')', NULL, &opt, NULL, "",
		  PARSE_OPT_NOARG | PARSE_OPT_NONEG | PARSE_OPT_NODASH,
		  close_callback },
		OPT_BOOLEAN('q', "quiet", &opt.status_only,
			    "indicate hit with exit status without output"),
		OPT_BOOLEAN(0, "all-match", &opt.all_match,
			"show only matches from files that match all patterns"),
		OPT_GROUP(""),
		{ OPTION_STRING, 'O', "open-files-in-pager", &show_in_pager,
			"pager", "show matching files in the pager",
			PARSE_OPT_OPTARG, NULL, (intptr_t)default_pager },
		OPT_BOOLEAN(0, "ext-grep", &external_grep_allowed__ignored,
			    "allow calling of grep(1) (ignored by this build)"),
		{ OPTION_CALLBACK, 0, "help-all", &options, NULL, "show usage",
		  PARSE_OPT_HIDDEN | PARSE_OPT_NOARG, help_callback },
		OPT_END()
	};

	/*
	 * 'git grep -h', unlike 'git grep -h <pattern>', is a request
	 * to show usage information and exit.
	 */
	if (argc == 2 && !strcmp(argv[1], "-h"))
		usage_with_options(grep_usage, options);

	memset(&opt, 0, sizeof(opt));
	opt.prefix = prefix;
	opt.prefix_length = (prefix && *prefix) ? strlen(prefix) : 0;
	opt.relative = 1;
	opt.pathname = 1;
	opt.pattern_tail = &opt.pattern_list;
	opt.header_tail = &opt.header_list;
	opt.regflags = REG_NEWLINE;
	opt.max_depth = -1;

	strcpy(opt.color_context, "");
	strcpy(opt.color_filename, "");
	strcpy(opt.color_function, "");
	strcpy(opt.color_lineno, "");
	strcpy(opt.color_match, GIT_COLOR_BOLD_RED);
	strcpy(opt.color_selected, "");
	strcpy(opt.color_sep, GIT_COLOR_CYAN);
	opt.color = -1;
	git_config(grep_config, &opt);
	if (opt.color == -1)
		opt.color = git_use_color_default;

	/*
	 * If there is no -- then the paths must exist in the working
	 * tree.  If there is no explicit pattern specified with -e or
	 * -f, we take the first unrecognized non option to be the
	 * pattern, but then what follows it must be zero or more
	 * valid refs up to the -- (if exists), and then existing
	 * paths.  If there is an explicit pattern, then the first
	 * unrecognized non option is the beginning of the refs list
	 * that continues up to the -- (if exists), and then paths.
	 */
	argc = parse_options(argc, argv, prefix, options, grep_usage,
			     PARSE_OPT_KEEP_DASHDASH |
			     PARSE_OPT_STOP_AT_NON_OPTION |
			     PARSE_OPT_NO_INTERNAL_HELP);

	if (use_index && !startup_info->have_repository)
		/* die the same way as if we did it at the beginning */
		setup_git_directory();

	/*
	 * skip a -- separator; we know it cannot be
	 * separating revisions from pathnames if
	 * we haven't even had any patterns yet
	 */
	if (argc > 0 && !opt.pattern_list && !strcmp(argv[0], "--")) {
		argv++;
		argc--;
	}

	/* First unrecognized non-option token */
	if (argc > 0 && !opt.pattern_list) {
		append_grep_pattern(&opt, argv[0], "command line", 0,
				    GREP_PATTERN);
		argv++;
		argc--;
	}

	if (show_in_pager == default_pager)
		show_in_pager = git_pager(1);
	if (show_in_pager) {
		opt.color = 0;
		opt.name_only = 1;
		opt.null_following_name = 1;
		opt.output_priv = &path_list;
		opt.output = append_path;
		string_list_append(&path_list, show_in_pager);
		use_threads = 0;
	}

	if (!opt.pattern_list)
		die("no pattern given.");
	if (!opt.fixed && opt.ignore_case)
		opt.regflags |= REG_ICASE;
	if ((opt.regflags != REG_NEWLINE) && opt.fixed)
		die("cannot mix --fixed-strings and regexp");

#ifndef NO_PTHREADS
	if (online_cpus() == 1 || !grep_threads_ok(&opt))
		use_threads = 0;

	if (use_threads) {
		if (opt.pre_context || opt.post_context)
			print_hunk_marks_between_files = 1;
		start_threads(&opt);
	}
#else
	use_threads = 0;
#endif

	compile_grep_patterns(&opt);

	/* Check revs and then paths */
	for (i = 0; i < argc; i++) {
		const char *arg = argv[i];
		unsigned char sha1[20];
		/* Is it a rev? */
		if (!get_sha1(arg, sha1)) {
			struct object *object = parse_object(sha1);
			if (!object)
				die("bad object %s", arg);
			add_object_array(object, arg, &list);
			continue;
		}
		if (!strcmp(arg, "--")) {
			i++;
			seen_dashdash = 1;
		}
		break;
	}

	/* The rest are paths */
	if (!seen_dashdash) {
		int j;
		for (j = i; j < argc; j++)
			verify_filename(prefix, argv[j]);
	}

	if (i < argc)
		paths = get_pathspec(prefix, argv + i);
	else if (prefix) {
		paths = xcalloc(2, sizeof(const char *));
		paths[0] = prefix;
		paths[1] = NULL;
	}

	if (show_in_pager && (cached || list.nr))
		die("--open-files-in-pager only works on the worktree");

	if (show_in_pager && opt.pattern_list && !opt.pattern_list->next) {
		const char *pager = path_list.items[0].string;
		int len = strlen(pager);

		if (len > 4 && is_dir_sep(pager[len - 5]))
			pager += len - 4;

		if (!strcmp("less", pager) || !strcmp("vi", pager)) {
			struct strbuf buf = STRBUF_INIT;
			strbuf_addf(&buf, "+/%s%s",
					strcmp("less", pager) ? "" : "*",
					opt.pattern_list->pattern);
			string_list_append(&path_list, buf.buf);
			strbuf_detach(&buf, NULL);
		}
	}

	if (!show_in_pager)
		setup_pager();


	if (!use_index) {
		if (cached)
			die("--cached cannot be used with --no-index.");
		if (list.nr)
			die("--no-index cannot be used with revs.");
		hit = grep_directory(&opt, paths);
	} else if (!list.nr) {
		if (!cached)
			setup_work_tree();

		hit = grep_cache(&opt, paths, cached);
	} else {
		if (cached)
			die("both --cached and trees are given.");
		hit = grep_objects(&opt, paths, &list);
	}

	if (use_threads)
		hit |= wait_all();
	if (hit && show_in_pager)
		run_pager(&opt, prefix);
	free_grep_patterns(&opt);
	return !hit;
}
Example #12
0
/*
 * Runs command in a subprocess. Returns pid on success and a FILE* to the
 * subprocess' stdout or 0 on failure.
 * NB. "command" is only used for logging.
 */
static pid_t
subprocess(const char *tag, struct passwd *pw, const char *command,
    int ac, char **av, FILE **child)
{
	FILE *f;
	struct stat st;
	int devnull, p[2], i;
	pid_t pid;
	char *cp, errmsg[512];
	u_int envsize;
	char **child_env;

	*child = NULL;

	debug3("%s: %s command \"%s\" running as %s", __func__,
	    tag, command, pw->pw_name);

	/* Verify the path exists and is safe-ish to execute */
	if (*av[0] != '/') {
		error("%s path is not absolute", tag);
		return 0;
	}
	temporarily_use_uid(pw);
	if (stat(av[0], &st) < 0) {
		error("Could not stat %s \"%s\": %s", tag,
		    av[0], strerror(errno));
		restore_uid();
		return 0;
	}
	if (auth_secure_path(av[0], &st, NULL, 0,
	    errmsg, sizeof(errmsg)) != 0) {
		error("Unsafe %s \"%s\": %s", tag, av[0], errmsg);
		restore_uid();
		return 0;
	}

	/*
	 * Run the command; stderr is left in place, stdout is the
	 * authorized_keys output.
	 */
	if (pipe(p) != 0) {
		error("%s: pipe: %s", tag, strerror(errno));
		restore_uid();
		return 0;
	}

	/*
	 * Don't want to call this in the child, where it can fatal() and
	 * run cleanup_exit() code.
	 */
	restore_uid();

	switch ((pid = fork())) {
	case -1: /* error */
		error("%s: fork: %s", tag, strerror(errno));
		close(p[0]);
		close(p[1]);
		return 0;
	case 0: /* child */
		/* Prepare a minimal environment for the child. */
		envsize = 5;
		child_env = xcalloc(sizeof(*child_env), envsize);
		child_set_env(&child_env, &envsize, "PATH", _PATH_STDPATH);
		child_set_env(&child_env, &envsize, "USER", pw->pw_name);
		child_set_env(&child_env, &envsize, "LOGNAME", pw->pw_name);
		child_set_env(&child_env, &envsize, "HOME", pw->pw_dir);
		if ((cp = getenv("LANG")) != NULL)
			child_set_env(&child_env, &envsize, "LANG", cp);

		for (i = 0; i < NSIG; i++)
			signal(i, SIG_DFL);

		if ((devnull = open(_PATH_DEVNULL, O_RDWR)) == -1) {
			error("%s: open %s: %s", tag, _PATH_DEVNULL,
			    strerror(errno));
			_exit(1);
		}
		/* Keep stderr around a while longer to catch errors */
		if (dup2(devnull, STDIN_FILENO) == -1 ||
		    dup2(p[1], STDOUT_FILENO) == -1) {
			error("%s: dup2: %s", tag, strerror(errno));
			_exit(1);
		}
		closefrom(STDERR_FILENO + 1);

		/* Don't use permanently_set_uid() here to avoid fatal() */
		if (setresgid(pw->pw_gid, pw->pw_gid, pw->pw_gid) != 0) {
			error("%s: setresgid %u: %s", tag, (u_int)pw->pw_gid,
			    strerror(errno));
			_exit(1);
		}
		if (setresuid(pw->pw_uid, pw->pw_uid, pw->pw_uid) != 0) {
			error("%s: setresuid %u: %s", tag, (u_int)pw->pw_uid,
			    strerror(errno));
			_exit(1);
		}
		/* stdin is pointed to /dev/null at this point */
		if (dup2(STDIN_FILENO, STDERR_FILENO) == -1) {
			error("%s: dup2: %s", tag, strerror(errno));
			_exit(1);
		}

		execve(av[0], av, child_env);
		error("%s exec \"%s\": %s", tag, command, strerror(errno));
		_exit(127);
	default: /* parent */
		break;
	}

	close(p[1]);
	if ((f = fdopen(p[0], "r")) == NULL) {
		error("%s: fdopen: %s", tag, strerror(errno));
		close(p[0]);
		/* Don't leave zombie child */
		kill(pid, SIGTERM);
		while (waitpid(pid, NULL, 0) == -1 && errno == EINTR)
			;
		return 0;
	}
	/* Success */
	debug3("%s: %s pid %ld", __func__, tag, (long)pid);
	*child = f;
	return pid;
}
Example #13
0
USHORT DMS_Process_File(struct zfile *fi, struct zfile *fo, USHORT cmd, USHORT opt, USHORT PCRC, USHORT pwd, int32_t part, struct zfile **extra)
{
	USHORT from, to, geninfo, c_version, cmode, hcrc, disktype, pv, ret;
	ULONG pkfsize, unpkfsize;
	UCHAR *b1, *b2;
	time_t date;

	passfound = 0;
	passretries = 2;
	b1 = xcalloc(UCHAR,TRACK_BUFFER_LEN);
	if (!b1) return ERR_NOMEMORY;
	b2 = xcalloc(UCHAR,TRACK_BUFFER_LEN);
	if (!b2) {
		xfree(b1);
		return ERR_NOMEMORY;
	}
	dms_text = xcalloc(UCHAR,TEMP_BUFFER_LEN);
	if (!dms_text) {
		xfree(b1);
		xfree(b2);
		return ERR_NOMEMORY;
	}

	/* if iname is NULL, input is stdin;   if oname is NULL, output is stdout */

	if (zfile_fread(b1,1,HEADLEN,fi) != HEADLEN) {
		xfree(b1);
		xfree(b2);
		xfree(dms_text);
		return ERR_SREAD;
	}

	if ( (b1[0] != 'D') || (b1[1] != 'M') || (b1[2] != 'S') || (b1[3] != '!') ) {
		/*  Check the first 4 bytes of file to see if it is "DMS!"  */
		xfree(b1);
		xfree(b2);
		xfree(dms_text);
		return ERR_NOTDMS;
	}

	hcrc = (USHORT)((b1[HEADLEN-2]<<8) | b1[HEADLEN-1]);
	/* Header CRC */

	if (hcrc != dms_CreateCRC(b1+4,(ULONG)(HEADLEN-6))) {
		xfree(b1);
		xfree(b2);
		xfree(dms_text);
		return ERR_HCRC;
	}

	geninfo = (USHORT) ((b1[10]<<8) | b1[11]);	/* General info about archive */
	date = (time_t) ((((ULONG)b1[12])<<24) | (((ULONG)b1[13])<<16) | (((ULONG)b1[14])<<8) | (ULONG)b1[15]);	/* date in standard UNIX/ANSI format */
	from = (USHORT) ((b1[16]<<8) | b1[17]);		/*  Lowest track in archive. May be incorrect if archive is "appended" */
	to = (USHORT) ((b1[18]<<8) | b1[19]);		/*  Highest track in archive. May be incorrect if archive is "appended" */

	if (part && from < 30) {
		xfree(b1);
		xfree(b2);
		xfree(dms_text);
		return DMS_FILE_END;
	}

	pkfsize = (ULONG) ((((ULONG)b1[21])<<16) | (((ULONG)b1[22])<<8) | (ULONG)b1[23]);	/*  Length of total packed data as in archive   */
	unpkfsize = (ULONG) ((((ULONG)b1[25])<<16) | (((ULONG)b1[26])<<8) | (ULONG)b1[27]);	/*  Length of unpacked data. Usually 901120 bytes  */

	c_version = (USHORT) ((b1[46]<<8) | b1[47]);	/*  version of DMS used to generate it  */
	disktype = (USHORT) ((b1[50]<<8) | b1[51]);		/*  Type of compressed disk  */
	cmode = (USHORT) ((b1[52]<<8) | b1[53]);        /*  Compression mode mostly used in this archive  */

	PWDCRC = PCRC;

	if (dolog) {

		pv = (USHORT)(c_version/100);
		write_log (" Created with DMS version %d.%02d ",pv,c_version-pv*100);
		if (geninfo & 0x80)
			write_log ("Registered\n");
		else
			write_log ("Evaluation\n");

		write_log (" Creation date : %s",ctime(&date));
		write_log (" Lowest track in archive : %d\n",from);
		write_log (" Highest track in archive : %d\n",to);
		write_log (" Packed data size : %lu\n",pkfsize);
		write_log (" Unpacked data size : %lu\n",unpkfsize);
		write_log (" Disk type of archive : ");

		/*  The original DMS from SDS software (DMS up to 1.11) used other values    */
		/*  in disk type to indicate formats as MS-DOS, AMax and Mac, but it was     */
		/*  not suported for compression. It was for future expansion and was never  */
		/*  used. The newer versions of DMS made by ParCon Software changed it to    */
		/*  add support for new Amiga disk types.                                    */
		switch (disktype) {
			case 0:
			case 1:
				/* Can also be a non-dos disk */
				write_log ("AmigaOS 1.0 OFS\n");
				break;
			case 2:
				write_log ("AmigaOS 2.0 FFS\n");
				break;
			case 3:
				write_log ("AmigaOS 3.0 OFS / International\n");
				break;
			case 4:
				write_log ("AmigaOS 3.0 FFS / International\n");
				break;
			case 5:
				write_log ("AmigaOS 3.0 OFS / Dir Cache\n");
				break;
			case 6:
				write_log ("AmigaOS 3.0 FFS / Dir Cache\n");
				break;
			case 7:
				write_log ("FMS Amiga System File\n");
				break;
			default:
				write_log ("Unknown\n");
		}

		write_log (" Compression mode used : ");
		if (cmode>6)
			write_log ("Unknown !\n");
		else
			write_log ("%s\n",modes[cmode]);

		write_log (" General info : ");
		if ((geninfo==0)||(geninfo==0x80)) write_log ("None");
		if (geninfo & 1) write_log ("NoZero ");
		if (geninfo & 2) write_log ("Encrypted ");
		if (geninfo & 4) write_log ("Appends ");
		if (geninfo & 8) write_log ("Banner ");
		if (geninfo & 16) write_log ("HD ");
		if (geninfo & 32) write_log ("MS-DOS ");
		if (geninfo & 64) write_log ("DMS_DEV_Fixed ");
		if (geninfo & 256) write_log ("FILEID.DIZ");
		write_log ("\n");

		write_log (" Info Header CRC : %04X\n\n",hcrc);

	}

	if (disktype == 7) {
		/*  It's not a DMS compressed disk image, but a FMS archive  */
		xfree(b1);
		xfree(b2);
		xfree(dms_text);
		return ERR_FMS;
	}


	if (dolog)	{
		write_log (" Track   Plength  Ulength  Cmode   USUM  HCRC  DCRC Cflag\n");
		write_log (" ------  -------  -------  ------  ----  ----  ---- -----\n");
	}

	//	if (((cmd==CMD_UNPACK) || (cmd==CMD_SHOWBANNER)) && (geninfo & 2) && (!pwd))
	//		return ERR_NOPASSWD;

	ret=NO_PROBLEM;

	Init_Decrunchers();

	if (cmd != CMD_VIEW) {
		if (cmd == CMD_SHOWBANNER) /*  Banner is in the first track  */
			ret = Process_Track(fi,NULL,b1,b2,cmd,opt,geninfo,extra);
		else {
			for (;;) {
				int32_t ok = 0;
				ret = Process_Track(fi,fo,b1,b2,cmd,opt,geninfo,extra);
				if (ret == DMS_FILE_END)
					break;
				if (ret == NO_PROBLEM)
					continue;
				break;
#if 0
				while (!ok) {
					uint8_t b1[THLEN];

					if (zfile_fread(b1,1,THLEN,fi) != 1) {
						write_log ("DMS: unexpected end of file\n");
						break;
					}
					write_log ("DMS: corrupted track, searching for next track header..\n");
					if (b1[0] == 'T' && b1[1] == 'R') {
						USHORT hcrc = (USHORT)((b1[THLEN-2] << 8) | b1[THLEN-1]);
						if (CreateCRC(b1,(ULONG)(THLEN-2)) == hcrc) {
							write_log ("DMS: found checksum correct track header, retrying..\n");
							zfile_fseek (fi, SEEK_CUR, -THLEN);
							ok = 1;
							break;
						}
					}
					if (!ok)
						zfile_fseek (fi, SEEK_CUR, -(THLEN - 1));
				}
#endif
			}
		}
	}

	if ((cmd == CMD_VIEWFULL) || (cmd == CMD_SHOWDIZ) || (cmd == CMD_SHOWBANNER)) write_log ("\n");

	if (ret == DMS_FILE_END) ret = NO_PROBLEM;


	/*  Used to give an error message, but I have seen some DMS  */
	/*  files with texts or zeros at the end of the valid data   */
	/*  So, when we find something that is not a track header,   */
	/*  we suppose that the valid data is over. And say it's ok. */
	if (ret == ERR_NOTTRACK) ret = NO_PROBLEM;


	xfree(b1);
	xfree(b2);
	xfree(dms_text);

	return ret;
}
Example #14
0
    VALUE
cb_bucket_observe(int argc, VALUE *argv, VALUE self)
{
    struct bucket_st *bucket = DATA_PTR(self);
    struct context_st *ctx;
    VALUE args, rv, proc, exc;
    lcb_error_t err;
    struct params_st params;

    if (bucket->handle == NULL) {
        rb_raise(eConnectError, "closed connection");
    }
    rb_scan_args(argc, argv, "0*&", &args, &proc);
    if (!bucket->async && proc != Qnil) {
        rb_raise(rb_eArgError, "synchronous mode doesn't support callbacks");
    }
    memset(&params, 0, sizeof(struct params_st));
    params.type = cmd_observe;
    params.bucket = bucket;
    cb_params_build(&params, RARRAY_LEN(args), args);
    ctx = xcalloc(1, sizeof(struct context_st));
    if (ctx == NULL) {
        rb_raise(eClientNoMemoryError, "failed to allocate memory for context");
    }
    ctx->proc = cb_gc_protect(bucket, proc);
    ctx->bucket = bucket;
    rv = rb_hash_new();
    ctx->rv = &rv;
    ctx->exception = Qnil;
    ctx->nqueries = params.cmd.observe.num;
    err = lcb_observe(bucket->handle, (const void *)ctx,
            params.cmd.observe.num, params.cmd.observe.ptr);
    cb_params_destroy(&params);
    exc = cb_check_error(err, "failed to schedule observe request", Qnil);
    if (exc != Qnil) {
        xfree(ctx);
        rb_exc_raise(exc);
    }
    bucket->nbytes += params.npayload;
    if (bucket->async) {
        maybe_do_loop(bucket);
        return Qnil;
    } else {
        if (ctx->nqueries > 0) {
            /* we have some operations pending */
            lcb_wait(bucket->handle);
        }
        exc = ctx->exception;
        xfree(ctx);
        if (exc != Qnil) {
            cb_gc_unprotect(bucket, exc);
            rb_exc_raise(exc);
        }
        if (bucket->exception != Qnil) {
            rb_exc_raise(bucket->exception);
        }
        if (params.cmd.observe.num > 1 || params.cmd.observe.array) {
            return rv;  /* return as a hash {key => {}, ...} */
        } else {
            VALUE vv = Qnil;
            rb_hash_foreach(rv, cb_first_value_i, (VALUE)&vv);
            return vv;  /* return first value */
        }
    }
}
Example #15
0
static int recycle (const TCHAR *name)
{
	DWORD dirattr = GetFileAttributesSafe (name);
	bool isdir = dirattr != INVALID_FILE_ATTRIBUTES && (dirattr & FILE_ATTRIBUTE_DIRECTORY);
	const TCHAR *namep;
	TCHAR path[MAX_DPATH];
	
	if (currprefs.win32_filesystem_mangle_reserved_names == false) {
		_tcscpy (path, PATHPREFIX);
		_tcscat (path, name);
		namep = path;
	} else {
		namep = name;
	}

	if (currprefs.win32_norecyclebin || isdir || currprefs.win32_filesystem_mangle_reserved_names == false) {
		if (isdir)
			return RemoveDirectory (namep) ? 0 : -1;
		else
			return DeleteFile (namep) ? 0 : -1;
	} else {
		SHFILEOPSTRUCT fos;
		HANDLE h;
		
		h = CreateFile (namep, GENERIC_READ, FILE_SHARE_READ | FILE_SHARE_WRITE, NULL,
			OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, NULL);
		if (h != INVALID_HANDLE_VALUE) {
			LARGE_INTEGER size;
			if (GetFileSizeEx (h, &size)) {
				if (size.QuadPart == 0) {
					CloseHandle (h);
					return DeleteFile (namep) ? 0 : -1;
				}
			}
			CloseHandle (h);
		}

		/* name must be terminated by \0\0 */
		TCHAR *p = xcalloc (TCHAR, _tcslen (namep) + 2);
		int v;

		_tcscpy (p, namep);
		memset (&fos, 0, sizeof (fos));
		fos.wFunc = FO_DELETE;
		fos.pFrom = p;
		fos.fFlags = FOF_ALLOWUNDO | FOF_NOCONFIRMATION | FOF_NOERRORUI | FOF_NORECURSION | FOF_SILENT;
		v = SHFileOperation (&fos);
		xfree (p);
		switch (v)
		{
		case 0xb7: //DE_ERROR_MAX
		case 0x7c: //DE_INVALIDFILES
		case 0x402: // "unknown error"
			v = ERROR_FILE_NOT_FOUND;
			break;
		case 0x75: //DE_OPCANCELLED:
		case 0x10000: //ERRORONDEST:
		case 0x78: //DE_ACCESSDENIEDSRC:
		case 0x74: //DE_ROOTDIR:
			v = ERROR_ACCESS_DENIED;
			break;
		}
		SetLastError (v);
		return v ? -1 : 0;
	}
}
Example #16
0
/*
 * Waits for the server identification string, and sends our own
 * identification string.
 */
void
ssh_exchange_identification(int timeout_ms)
{
	char buf[256], remote_version[256];	/* must be same size! */
	int remote_major, remote_minor, mismatch;
	int connection_in = packet_get_connection_in();
	int connection_out = packet_get_connection_out();
	int minor1 = PROTOCOL_MINOR_1;
	u_int i, n;
	size_t len;
	int fdsetsz, remaining, rc;
	struct timeval t_start, t_remaining;
	fd_set *fdset;

	fdsetsz = howmany(connection_in + 1, NFDBITS) * sizeof(fd_mask);
	fdset = xcalloc(1, fdsetsz);

	/* Read other side's version identification. */
	remaining = timeout_ms;
	for (n = 0;;) {
		for (i = 0; i < sizeof(buf) - 1; i++) {
			if (timeout_ms > 0) {
				gettimeofday(&t_start, NULL);
				ms_to_timeval(&t_remaining, remaining);
				FD_SET(connection_in, fdset);
				rc = select(connection_in + 1, fdset, NULL,
				    fdset, &t_remaining);
				ms_subtract_diff(&t_start, &remaining);
				if (rc == 0 || remaining <= 0)
					fatal("Connection timed out during "
					    "banner exchange");
				if (rc == -1) {
					if (errno == EINTR)
						continue;
					fatal("ssh_exchange_identification: "
					    "select: %s", strerror(errno));
				}
			}

			len = roaming_atomicio(read, connection_in, &buf[i], 1);

			if (len != 1 && errno == EPIPE)
				fatal("ssh_exchange_identification: "
				    "Connection closed by remote host");
			else if (len != 1)
				fatal("ssh_exchange_identification: "
				    "read: %.100s", strerror(errno));
			if (buf[i] == '\r') {
				buf[i] = '\n';
				buf[i + 1] = 0;
				continue;		/**XXX wait for \n */
			}
			if (buf[i] == '\n') {
				buf[i + 1] = 0;
				break;
			}
			if (++n > 65536)
				fatal("ssh_exchange_identification: "
				    "No banner received");
		}
		buf[sizeof(buf) - 1] = 0;
		if (strncmp(buf, "SSH-", 4) == 0)
			break;
		debug("ssh_exchange_identification: %s", buf);
	}
	server_version_string = xstrdup(buf);
	xfree(fdset);

	/*
	 * Check that the versions match.  In future this might accept
	 * several versions and set appropriate flags to handle them.
	 */
	if (sscanf(server_version_string, "SSH-%d.%d-%[^\n]\n",
	    &remote_major, &remote_minor, remote_version) != 3)
		fatal("Bad remote protocol version identification: '%.100s'", buf);
	debug("Remote protocol version %d.%d, remote software version %.100s",
	    remote_major, remote_minor, remote_version);

	compat_datafellows(remote_version);
	mismatch = 0;

	switch (remote_major) {
	case 1:
		if (remote_minor == 99 &&
		    (options.protocol & SSH_PROTO_2) &&
		    !(options.protocol & SSH_PROTO_1_PREFERRED)) {
			enable_compat20();
			break;
		}
		if (!(options.protocol & SSH_PROTO_1)) {
			mismatch = 1;
			break;
		}
		if (remote_minor < 3) {
			fatal("Remote machine has too old SSH software version.");
		} else if (remote_minor == 3 || remote_minor == 4) {
			/* We speak 1.3, too. */
			enable_compat13();
			minor1 = 3;
			if (options.forward_agent) {
				logit("Agent forwarding disabled for protocol 1.3");
				options.forward_agent = 0;
			}
		}
		break;
	case 2:
		if (options.protocol & SSH_PROTO_2) {
			enable_compat20();
			break;
		}
		/* FALLTHROUGH */
	default:
		mismatch = 1;
		break;
	}
	if (mismatch)
		fatal("Protocol major versions differ: %d vs. %d",
		    (options.protocol & SSH_PROTO_2) ? PROTOCOL_MAJOR_2 : PROTOCOL_MAJOR_1,
		    remote_major);
	/* Send our own protocol version identification. */
	snprintf(buf, sizeof buf, "SSH-%d.%d-%.100s%s",
	    compat20 ? PROTOCOL_MAJOR_2 : PROTOCOL_MAJOR_1,
	    compat20 ? PROTOCOL_MINOR_2 : minor1,
	    ssh_version_get(options.hpn_disabled), compat20 ? "\r\n" : "\n");
	if (roaming_atomicio(vwrite, connection_out, buf, strlen(buf))
	    != strlen(buf))
		fatal("write: %.100s", strerror(errno));
	client_version_string = xstrdup(buf);
	chop(client_version_string);
	chop(server_version_string);
	debug("Local version string %.100s", client_version_string);
}
Example #17
0
/* Walk through the table and remove all entries which lifetime ended.

   We have a problem here.  To actually remove the entries we must get
   the write-lock.  But since we want to keep the time we have the
   lock as short as possible we cannot simply acquire the lock when we
   start looking for timedout entries.

   Therefore we do it in two stages: first we look for entries which
   must be invalidated and remember them.  Then we get the lock and
   actually remove them.  This is complicated by the way we have to
   free the data structures since some hash table entries share the same
   data.  */
time_t
prune_cache (struct database_dyn *table, time_t now, int fd)
{
    size_t cnt = table->head->module;

    /* If this table is not actually used don't do anything.  */
    if (cnt == 0)
    {
        if (fd != -1)
        {
            /* Reply to the INVALIDATE initiator.  */
            int32_t resp = 0;
            writeall (fd, &resp, sizeof (resp));
        }

        /* No need to do this again anytime soon.  */
        return 24 * 60 * 60;
    }

    /* If we check for the modification of the underlying file we invalidate
       the entries also in this case.  */
    if (table->check_file && now != LONG_MAX)
    {
        struct traced_file *runp = table->traced_files;

        while (runp != NULL)
        {
#ifdef HAVE_INOTIFY
            if (runp->inotify_descr == -1)
#endif
            {
                struct stat64 st;

                if (stat64 (runp->fname, &st) < 0)
                {
                    char buf[128];
                    /* We cannot stat() the file, disable file checking if the
                       file does not exist.  */
                    dbg_log (_("cannot stat() file `%s': %s"),
                             runp->fname, strerror_r (errno, buf, sizeof (buf)));
                    if (errno == ENOENT)
                        table->check_file = 0;
                }
                else
                {
                    if (st.st_mtime != table->file_mtime)
                    {
                        /* The file changed.  Invalidate all entries.  */
                        now = LONG_MAX;
                        table->file_mtime = st.st_mtime;
                    }
                }
            }

            runp = runp->next;
        }
    }

    /* We run through the table and find values which are not valid anymore.

       Note that for the initial step, finding the entries to be removed,
       we don't need to get any lock.  It is at all timed assured that the
       linked lists are set up correctly and that no second thread prunes
       the cache.  */
    bool *mark;
    size_t memory_needed = cnt * sizeof (bool);
    bool mark_use_alloca;
    if (__builtin_expect (memory_needed <= MAX_STACK_USE, 1))
    {
        mark = alloca (cnt * sizeof (bool));
        memset (mark, '\0', memory_needed);
        mark_use_alloca = true;
    }
    else
    {
        mark = xcalloc (1, memory_needed);
        mark_use_alloca = false;
    }
    size_t first = cnt + 1;
    size_t last = 0;
    char *const data = table->data;
    bool any = false;

    if (__builtin_expect (debug_level > 2, 0))
        dbg_log (_("pruning %s cache; time %ld"),
                 dbnames[table - dbs], (long int) now);

#define NO_TIMEOUT LONG_MAX
    time_t next_timeout = NO_TIMEOUT;
    do
    {
        ref_t run = table->head->array[--cnt];

        while (run != ENDREF)
        {
            struct hashentry *runp = (struct hashentry *) (data + run);
            struct datahead *dh = (struct datahead *) (data + runp->packet);

            /* Some debug support.  */
            if (__builtin_expect (debug_level > 2, 0))
            {
                char buf[INET6_ADDRSTRLEN];
                const char *str;

                if (runp->type == GETHOSTBYADDR || runp->type == GETHOSTBYADDRv6)
                {
                    inet_ntop (runp->type == GETHOSTBYADDR ? AF_INET : AF_INET6,
                               data + runp->key, buf, sizeof (buf));
                    str = buf;
                }
                else
                    str = data + runp->key;

                dbg_log (_("considering %s entry \"%s\", timeout %" PRIu64),
                         serv2str[runp->type], str, dh->timeout);
            }

            /* Check whether the entry timed out.  */
            if (dh->timeout < now)
            {
                /* This hash bucket could contain entries which need to
                be looked at.  */
                mark[cnt] = true;

                first = MIN (first, cnt);
                last = MAX (last, cnt);

                /* We only have to look at the data of the first entries
                since the count information is kept in the data part
                 which is shared.  */
                if (runp->first)
                {

                    /* At this point there are two choices: we reload the
                       value or we discard it.  Do not change NRELOADS if
                       we never not reload the record.  */
                    if ((reload_count != UINT_MAX
                            && __builtin_expect (dh->nreloads >= reload_count, 0))
                            /* We always remove negative entries.  */
                            || dh->notfound
                            /* Discard everything if the user explicitly
                            requests it.  */
                            || now == LONG_MAX)
                    {
                        /* Remove the value.  */
                        dh->usable = false;

                        /* We definitely have some garbage entries now.  */
                        any = true;
                    }
                    else
                    {
                        /* Reload the value.  We do this only for the
                        initially used key, not the additionally
                         added derived value.  */
                        assert (runp->type < LASTREQ
                                && readdfcts[runp->type] != NULL);

                        time_t timeout = readdfcts[runp->type] (table, runp, dh);
                        next_timeout = MIN (next_timeout, timeout);

                        /* If the entry has been replaced, we might need
                        cleanup.  */
                        any |= !dh->usable;
                    }
                }
            }
            else
            {
                assert (dh->usable);
                next_timeout = MIN (next_timeout, dh->timeout);
            }

            run = runp->next;
        }
    }
    while (cnt > 0);

    if (__builtin_expect (fd != -1, 0))
    {
        /* Reply to the INVALIDATE initiator that the cache has been
        invalidated.  */
        int32_t resp = 0;
        writeall (fd, &resp, sizeof (resp));
    }

    if (first <= last)
    {
        struct hashentry *head = NULL;

        /* Now we have to get the write lock since we are about to modify
        the table.  */
        if (__builtin_expect (pthread_rwlock_trywrlock (&table->lock) != 0, 0))
        {
            ++table->head->wrlockdelayed;
            pthread_rwlock_wrlock (&table->lock);
        }

        while (first <= last)
        {
            if (mark[first])
            {
                ref_t *old = &table->head->array[first];
                ref_t run = table->head->array[first];

                assert (run != ENDREF);
                do
                {
                    struct hashentry *runp = (struct hashentry *) (data + run);
                    struct datahead *dh
                        = (struct datahead *) (data + runp->packet);

                    if (! dh->usable)
                    {
                        /* We need the list only for debugging but it is
                        more costly to avoid creating the list than
                         doing it.  */
                        runp->dellist = head;
                        head = runp;

                        /* No need for an atomic operation, we have the
                        write lock.  */
                        --table->head->nentries;

                        run = *old = runp->next;
                    }
                    else
                    {
                        old = &runp->next;
                        run = runp->next;
                    }
                }
                while (run != ENDREF);
            }

            ++first;
        }

        /* It's all done.  */
        pthread_rwlock_unlock (&table->lock);

        /* Make sure the data is saved to disk.  */
        if (table->persistent)
            msync (table->head,
                   data + table->head->first_free - (char *) table->head,
                   MS_ASYNC);

        /* One extra pass if we do debugging.  */
        if (__builtin_expect (debug_level > 0, 0))
        {
            struct hashentry *runp = head;

            while (runp != NULL)
            {
                char buf[INET6_ADDRSTRLEN];
                const char *str;

                if (runp->type == GETHOSTBYADDR || runp->type == GETHOSTBYADDRv6)
                {
                    inet_ntop (runp->type == GETHOSTBYADDR ? AF_INET : AF_INET6,
                               data + runp->key, buf, sizeof (buf));
                    str = buf;
                }
                else
                    str = data + runp->key;

                dbg_log ("remove %s entry \"%s\"", serv2str[runp->type], str);

                runp = runp->dellist;
            }
        }
    }

    if (__builtin_expect (! mark_use_alloca, 0))
        free (mark);

    /* Run garbage collection if any entry has been removed or replaced.  */
    if (any)
        gc (table);

    /* If there is no entry in the database and we therefore have no new
       timeout value, tell the caller to wake up in 24 hours.  */
    return next_timeout == NO_TIMEOUT ? 24 * 60 * 60 : next_timeout - now;
}
Example #18
0
void
parsetab(void)
{
	FILE *fp;
	const char *tab;
	char *cp, *p, *line, *opt;
	size_t len;
	struct autoentry *ent;
	int i, lineno, x, gotopt;
	const char *expecting = "expecting 'direct', 'indirect' or 'browse'";
	const char *tabfiles[] = {
		"/etc/autotab", "/usr/local/etc/autotab", "./autotab", NULL
	};

	lineno = 0;
	for (i = 0; (tab = tabfiles[i]) != NULL; i++) {
		tab = tabfiles[i];
		fp = fopen(tab, "r");
		if (fp == NULL)
			warn("fopen %s", tab);
		if (fp != NULL)
			break;
	}
	if (fp == NULL) {
		err(1, "no config file available.");
	}

	fprintf(stderr, "using config file: %s\n", tab);

	while ((cp = fgetln(fp, &len)) != NULL) {
		lineno++;
		while (len > 0 && isspace(cp[len - 1]))
			len--;
		line = xmalloc(len + 1);
		bcopy(cp, line, len);
		line[len] = '\0';
		cp = line;
		if ((cp = strchr(line, '#')) != NULL)
			*cp = '\0';
		cp = line;
		while (isspace(*cp))
			cp++;
		if (*cp == '\0') {
			free(line);
			continue;
		}
		ent = xcalloc(1, sizeof(*ent));
		if ((p = strsep(&cp, " \t")) == NULL)
			goto bad;
		ent->ae_mnt = p;
		if ((p = strsep(&cp, " \t")) == NULL)
			goto bad;
		ent->ae_path = p;
		if ((p = strsep(&cp, " \t")) == NULL)
			goto bad;
		ent->ae_type = p;
		if ((p = strsep(&cp, " \t")) == NULL)
			goto bad;
		ent->ae_opts = p;
		if ((p = strsep(&cp, " \t")) == NULL)
			goto bad;
		ent->ae_rpath = p;
		if ((p = strsep(&cp, " \t")) == NULL)
			goto bad;
		gotopt = 0;
		opt = p;
		while ((p = strsep(&opt, ",")) != NULL) {
			if (strcmp(p, "indirect") == 0) {
				ent->ae_indirect = 1;
				gotopt = 1;
			} else if (strcmp(p, "direct") == 0) {
				ent->ae_direct = 1;
				gotopt = 1;
			} else if (strcmp(p, "browse") == 0) {
				ent->ae_browse = 1;
				gotopt = 1;
			} else {
				warnx("unreconized option '%s', %s",
				    p, expecting);
				goto bad2;
			}
		}
		if (!gotopt) {
			warnx("no options specified %s", expecting);
			goto bad2;
		}
		if (ent->ae_direct && ent->ae_indirect) {
			warnx("direct and indirect are mutually exclusive");
			goto bad2;

		}
		x = asprintf(&ent->ae_fullpath, "%s/%s",
		    ent->ae_mnt, ent->ae_path);
		if (x == -1)
			err(1, "asprintf");

		if (strlen(ent->ae_fullpath) + 1 > PATH_MAX) {
			warnx("Error in file %s, line %d, "
			    "mountpath (%s) exceeds PATH_MAX (%d)",
			    tab, lineno, ent->ae_fullpath, PATH_MAX);
			goto bad2;
		}
		ent->ae_line = lineno;
		ent->ae_free = line;
		ent->ae_next = entries;
		entries = ent;
		continue;
bad:
		warnx("Parse error in file %s, line %d", tab, lineno);
bad2:
		free(ent->ae_fullpath);
		free(line);
		free(ent);
	}
	if (ferror(fp))
		err(1, "error with file %s", tab);
}
Example #19
0
static int
timeout_connect(int sockfd, const struct sockaddr *serv_addr,
    socklen_t addrlen, int *timeoutp)
{
	fd_set *fdset;
	struct timeval tv, t_start;
	socklen_t optlen;
	int optval, rc, result = -1;

	gettimeofday(&t_start, NULL);

	if (*timeoutp <= 0) {
		result = connect(sockfd, serv_addr, addrlen);
		goto done;
	}

	set_nonblock(sockfd);
	rc = connect(sockfd, serv_addr, addrlen);
	if (rc == 0) {
		unset_nonblock(sockfd);
		result = 0;
		goto done;
	}
	if (errno != EINPROGRESS) {
		result = -1;
		goto done;
	}

	fdset = (fd_set *)xcalloc(howmany(sockfd + 1, NFDBITS),
	    sizeof(fd_mask));
	FD_SET(sockfd, fdset);
	ms_to_timeval(&tv, *timeoutp);

	for (;;) {
		rc = select(sockfd + 1, NULL, fdset, NULL, &tv);
		if (rc != -1 || errno != EINTR)
			break;
	}

	switch (rc) {
	case 0:
		/* Timed out */
		errno = ETIMEDOUT;
		break;
	case -1:
		/* Select error */
		debug("select: %s", strerror(errno));
		break;
	case 1:
		/* Completed or failed */
		optval = 0;
		optlen = sizeof(optval);
		if (getsockopt(sockfd, SOL_SOCKET, SO_ERROR, &optval,
		    &optlen) == -1) {
			debug("getsockopt: %s", strerror(errno));
			break;
		}
		if (optval != 0) {
			errno = optval;
			break;
		}
		result = 0;
		unset_nonblock(sockfd);
		break;
	default:
		/* Should not occur */
		fatal("Bogus return (%d) from select()", rc);
	}

	xfree(fdset);

 done:
 	if (result == 0 && *timeoutp > 0) {
		ms_subtract_diff(&t_start, timeoutp);
		if (*timeoutp <= 0) {
			errno = ETIMEDOUT;
			result = -1;
		}
	}

	return (result);
}
Example #20
0
static void threaded_lazy_init_name_hash(
	struct index_state *istate)
{
	int nr_each;
	int k_start;
	int t;
	struct lazy_entry *lazy_entries;
	struct lazy_dir_thread_data *td_dir;
	struct lazy_name_thread_data *td_name;

	k_start = 0;
	nr_each = DIV_ROUND_UP(istate->cache_nr, lazy_nr_dir_threads);

	lazy_entries = xcalloc(istate->cache_nr, sizeof(struct lazy_entry));
	td_dir = xcalloc(lazy_nr_dir_threads, sizeof(struct lazy_dir_thread_data));
	td_name = xcalloc(1, sizeof(struct lazy_name_thread_data));

	init_dir_mutex();

	/*
	 * Phase 1:
	 * Build "istate->dir_hash" using n "dir" threads (and a read-only index).
	 */
	for (t = 0; t < lazy_nr_dir_threads; t++) {
		struct lazy_dir_thread_data *td_dir_t = td_dir + t;
		td_dir_t->istate = istate;
		td_dir_t->lazy_entries = lazy_entries;
		td_dir_t->k_start = k_start;
		k_start += nr_each;
		if (k_start > istate->cache_nr)
			k_start = istate->cache_nr;
		td_dir_t->k_end = k_start;
		if (pthread_create(&td_dir_t->pthread, NULL, lazy_dir_thread_proc, td_dir_t))
			die("unable to create lazy_dir_thread");
	}
	for (t = 0; t < lazy_nr_dir_threads; t++) {
		struct lazy_dir_thread_data *td_dir_t = td_dir + t;
		if (pthread_join(td_dir_t->pthread, NULL))
			die("unable to join lazy_dir_thread");
	}

	/*
	 * Phase 2:
	 * Iterate over all index entries and add them to the "istate->name_hash"
	 * using a single "name" background thread.
	 * (Testing showed it wasn't worth running more than 1 thread for this.)
	 *
	 * Meanwhile, finish updating the parent directory ref-counts for each
	 * index entry using the current thread.  (This step is very fast and
	 * doesn't need threading.)
	 */
	td_name->istate = istate;
	td_name->lazy_entries = lazy_entries;
	if (pthread_create(&td_name->pthread, NULL, lazy_name_thread_proc, td_name))
		die("unable to create lazy_name_thread");

	lazy_update_dir_ref_counts(istate, lazy_entries);

	if (pthread_join(td_name->pthread, NULL))
		die("unable to join lazy_name_thread");

	cleanup_dir_mutex();

	free(td_name);
	free(td_dir);
	free(lazy_entries);
}
Example #21
0
int lpf_factorize(LPF *lpf, int m, const int bh[], int (*col)
      (void *info, int j, int ind[], double val[]), void *info)
{     int k, ret;
#if _GLPLPF_DEBUG
      int i, j, len, *ind;
      double *B, *val;
#endif
      xassert(bh == bh);
      if (m < 1)
         xfault("lpf_factorize: m = %d; invalid parameter\n", m);
      if (m > M_MAX)
         xfault("lpf_factorize: m = %d; matrix too big\n", m);
      lpf->m0 = lpf->m = m;
      /* invalidate the factorization */
      lpf->valid = 0;
      /* allocate/reallocate arrays, if necessary */
      if (lpf->R_ptr == NULL)
         lpf->R_ptr = xcalloc(1+lpf->n_max, sizeof(int));
      if (lpf->R_len == NULL)
         lpf->R_len = xcalloc(1+lpf->n_max, sizeof(int));
      if (lpf->S_ptr == NULL)
         lpf->S_ptr = xcalloc(1+lpf->n_max, sizeof(int));
      if (lpf->S_len == NULL)
         lpf->S_len = xcalloc(1+lpf->n_max, sizeof(int));
      if (lpf->scf == NULL)
         lpf->scf = scf_create_it(lpf->n_max);
      if (lpf->v_ind == NULL)
         lpf->v_ind = xcalloc(1+lpf->v_size, sizeof(int));
      if (lpf->v_val == NULL)
         lpf->v_val = xcalloc(1+lpf->v_size, sizeof(double));
      if (lpf->m0_max < m)
      {  if (lpf->P_row != NULL) xfree(lpf->P_row);
         if (lpf->P_col != NULL) xfree(lpf->P_col);
         if (lpf->Q_row != NULL) xfree(lpf->Q_row);
         if (lpf->Q_col != NULL) xfree(lpf->Q_col);
         if (lpf->work1 != NULL) xfree(lpf->work1);
         if (lpf->work2 != NULL) xfree(lpf->work2);
         lpf->m0_max = m + 100;
         lpf->P_row = xcalloc(1+lpf->m0_max+lpf->n_max, sizeof(int));
         lpf->P_col = xcalloc(1+lpf->m0_max+lpf->n_max, sizeof(int));
         lpf->Q_row = xcalloc(1+lpf->m0_max+lpf->n_max, sizeof(int));
         lpf->Q_col = xcalloc(1+lpf->m0_max+lpf->n_max, sizeof(int));
         lpf->work1 = xcalloc(1+lpf->m0_max+lpf->n_max, sizeof(double));
         lpf->work2 = xcalloc(1+lpf->m0_max+lpf->n_max, sizeof(double));
      }
      /* try to factorize the basis matrix */
      switch (luf_factorize(lpf->luf, m, col, info))
      {  case 0:
            break;
         case LUF_ESING:
            ret = LPF_ESING;
            goto done;
         case LUF_ECOND:
            ret = LPF_ECOND;
            goto done;
         default:
            xassert(lpf != lpf);
      }
      /* the basis matrix has been successfully factorized */
      lpf->valid = 1;
#if _GLPLPF_DEBUG
      /* store the basis matrix for debugging */
      if (lpf->B != NULL) xfree(lpf->B);
      xassert(m <= 32767);
      lpf->B = B = xcalloc(1+m*m, sizeof(double));
      ind = xcalloc(1+m, sizeof(int));
      val = xcalloc(1+m, sizeof(double));
      for (k = 1; k <= m * m; k++)
         B[k] = 0.0;
      for (j = 1; j <= m; j++)
      {  len = col(info, j, ind, val);
         xassert(0 <= len && len <= m);
         for (k = 1; k <= len; k++)
         {  i = ind[k];
            xassert(1 <= i && i <= m);
            xassert(B[(i - 1) * m + j] == 0.0);
            xassert(val[k] != 0.0);
            B[(i - 1) * m + j] = val[k];
         }
      }
      xfree(ind);
      xfree(val);
#endif
      /* B = B0, so there are no additional rows/columns */
      lpf->n = 0;
      /* reset the Schur complement factorization */
      scf_reset_it(lpf->scf);
      /* P := Q := I */
      for (k = 1; k <= m; k++)
      {  lpf->P_row[k] = lpf->P_col[k] = k;
         lpf->Q_row[k] = lpf->Q_col[k] = k;
      }
      /* make all SVA locations free */
      lpf->v_ptr = 1;
      ret = 0;
done: /* return to the calling program */
      return ret;
}
Example #22
0
static void load_subtree(struct notes_tree *t, struct leaf_node *subtree,
		struct int_node *node, unsigned int n)
{
	unsigned char object_sha1[20];
	unsigned int prefix_len;
	void *buf;
	struct tree_desc desc;
	struct name_entry entry;
	int len, path_len;
	unsigned char type;
	struct leaf_node *l;

	buf = fill_tree_descriptor(&desc, subtree->val_sha1);
	if (!buf)
		die("Could not read %s for notes-index",
		     sha1_to_hex(subtree->val_sha1));

	prefix_len = subtree->key_sha1[19];
	assert(prefix_len * 2 >= n);
	memcpy(object_sha1, subtree->key_sha1, prefix_len);
	while (tree_entry(&desc, &entry)) {
		path_len = strlen(entry.path);
		len = get_sha1_hex_segment(entry.path, path_len,
				object_sha1 + prefix_len, 20 - prefix_len);
		if (len < 0)
			goto handle_non_note; /* entry.path is not a SHA1 */
		len += prefix_len;

		/*
		 * If object SHA1 is complete (len == 20), assume note object
		 * If object SHA1 is incomplete (len < 20), and current
		 * component consists of 2 hex chars, assume note subtree
		 */
		if (len <= 20) {
			type = PTR_TYPE_NOTE;
			l = (struct leaf_node *)
				xcalloc(sizeof(struct leaf_node), 1);
			hashcpy(l->key_sha1, object_sha1);
			hashcpy(l->val_sha1, entry.sha1);
			if (len < 20) {
				if (!S_ISDIR(entry.mode) || path_len != 2)
					goto handle_non_note; /* not subtree */
				l->key_sha1[19] = (unsigned char) len;
				type = PTR_TYPE_SUBTREE;
			}
			if (note_tree_insert(t, node, n, l, type,
					     combine_notes_concatenate))
				die("Failed to load %s %s into notes tree "
				    "from %s",
				    type == PTR_TYPE_NOTE ? "note" : "subtree",
				    sha1_to_hex(l->key_sha1), t->ref);
		}
		continue;

handle_non_note:
		/*
		 * Determine full path for this non-note entry:
		 * The filename is already found in entry.path, but the
		 * directory part of the path must be deduced from the subtree
		 * containing this entry. We assume here that the overall notes
		 * tree follows a strict byte-based progressive fanout
		 * structure (i.e. using 2/38, 2/2/36, etc. fanouts, and not
		 * e.g. 4/36 fanout). This means that if a non-note is found at
		 * path "dead/beef", the following code will register it as
		 * being found on "de/ad/beef".
		 * On the other hand, if you use such non-obvious non-note
		 * paths in the middle of a notes tree, you deserve what's
		 * coming to you ;). Note that for non-notes that are not
		 * SHA1-like at the top level, there will be no problems.
		 *
		 * To conclude, it is strongly advised to make sure non-notes
		 * have at least one non-hex character in the top-level path
		 * component.
		 */
		{
			char non_note_path[PATH_MAX];
			char *p = non_note_path;
			const char *q = sha1_to_hex(subtree->key_sha1);
			int i;
			for (i = 0; i < prefix_len; i++) {
				*p++ = *q++;
				*p++ = *q++;
				*p++ = '/';
			}
			strcpy(p, entry.path);
			add_non_note(t, non_note_path, entry.mode, entry.sha1);
		}
	}
	free(buf);
}
Example #23
0
int validate_bfs_result(const csr_graph* const g, const int64_t root, const int64_t* const pred, const int64_t nvisited) {
  int validation_passed = 1;
  int root_is_mine = (VERTEX_OWNER(root) == rank);

  const size_t nlocalverts = g->nlocalverts;
  const size_t nlocaledges = g->nlocaledges;
  const int64_t nglobalverts = g->nglobalverts;

  /* Check that root is its own parent. */
  if (root_is_mine) {
    if (pred[VERTEX_LOCAL(root)] != root) {
      fprintf(stderr, "%d: Validation error: parent of root vertex %" PRId64 " is %" PRId64 ", not the root itself.\n", rank, root, pred[VERTEX_LOCAL(root)]);
      validation_passed = 0;
    }
  }

  /* Check that nothing else is its own parent, and check for in-range
   * values. */
  int any_range_errors = 0;
  size_t i;
  for (i = 0; i < nlocalverts; ++i) {
    int64_t v = VERTEX_TO_GLOBAL(i);
    assert (VERTEX_OWNER(v) == rank);
    assert (VERTEX_LOCAL(v) == i);
    if (v != root && pred[i] == v) {
      fprintf(stderr, "%d: Validation error: parent of non-root vertex %" PRId64 " is itself.\n", rank, v);
      validation_passed = 0;
    }
    if (pred[i] < -1 || pred[i] >= nglobalverts) {
      fprintf(stderr, "%d: Validation error: parent of vertex %" PRId64 " is out-of-range value %" PRId64 ".\n", rank, v, pred[i]);
      validation_passed = 0;
      any_range_errors = 1;
    }
  }
  MPI_Allreduce(MPI_IN_PLACE, &any_range_errors, 1, MPI_INT, MPI_LOR, MPI_COMM_WORLD);

  /* Check that nvisited is correct. */
  int64_t nvisited_actual = 0;
  for (i = 0; i < nlocalverts; ++i) {
    if (pred[i] != -1) ++nvisited_actual;
  }
  MPI_Allreduce(MPI_IN_PLACE, &nvisited_actual, 1, INT64_T_MPI_TYPE, MPI_SUM, MPI_COMM_WORLD);
  if (nvisited_actual != nvisited) {
    fprintf(stderr, "%d: Validation error: claimed visit count %" PRId64 " is different from actual count %" PRId64 ".\n", rank, nvisited, nvisited_actual);
    validation_passed = 0;
  }

  if (!any_range_errors) { /* Other parts of validation assume in-range values */

    /* Check that there is an edge from each vertex to its claimed
     * predecessor. */
    size_t i;
    for (i = 0; i < nlocalverts; ++i) {
      int64_t v = VERTEX_TO_GLOBAL(i);
      int64_t p = pred[i];
      if (p == -1) continue;
      int found_pred_edge = 0;
      if (v == p) found_pred_edge = 1; /* Root vertex */
      size_t ei, ei_end = g->rowstarts[i + 1];
      for (ei = g->rowstarts[i]; ei < ei_end; ++ei) {
        int64_t w = g->column[ei];
        if (w == p) {
          found_pred_edge = 1;
          break;
        }
      }
      if (!found_pred_edge) {
        fprintf(stderr, "%d: Validation error: no graph edge from vertex %" PRId64 " to its parent %" PRId64 ".\n", rank, v, p);
        validation_passed = 0;
      }
    }

    /* Create a vertex depth map to use for later validation. */
    int64_t* depth = (int64_t*)xmalloc(nlocalverts * sizeof(int64_t));
    { /* Scope some code that has a lot of temporary variables. */
      int64_t* pred_depth = (int64_t*)xmalloc(nlocalverts * sizeof(int64_t)); /* Depth of predecessor vertex for each local vertex */
      size_t i;
      for (i = 0; i < nlocalverts; ++i) depth[i] = INT64_MAX;
      if (root_is_mine) depth[VERTEX_LOCAL(root)] = 0;
      /* Send each vertex that appears in the local part of the predecessor map
       * to its owner; record the original locations so we can put the answers
       * into pred_depth. */
      /* Do a histogram sort by owner (this same kind of sort is used other
       * places as well).  First, count the number of vertices going to each
       * destination. */
      int* num_preds_per_owner = (int*)xcalloc(size, sizeof(int)); /* Uses zero-init */
      for (i = 0; i < nlocalverts; ++i) {
        ++num_preds_per_owner[pred[i] == -1 ? size - 1 : VERTEX_OWNER(pred[i])];
      }
      int64_t* preds_per_owner = (int64_t*)xmalloc(nlocalverts * sizeof(int64_t)); /* Predecessors sorted by owner */
      int64_t* preds_per_owner_results_offsets = (int64_t*)xmalloc(nlocalverts * sizeof(int64_t)); /* Indices into pred_depth to write */
      /* Second, do a prefix sum to get the displacements of the different
       * owners in the outgoing array. */
      int* pred_owner_displs = (int*)xmalloc((size + 1) * sizeof(int));
      pred_owner_displs[0] = 0;
      int r;
      for (r = 0; r < size; ++r) {
        pred_owner_displs[r + 1] = pred_owner_displs[r] + num_preds_per_owner[r];
      }
      /* Last, put the vertices into the correct positions in the array, based
       * on their owners and the counts and displacements computed earlier. */
      int* pred_owner_offsets = (int*)xmalloc((size + 1) * sizeof(int));
      memcpy(pred_owner_offsets, pred_owner_displs, (size + 1) * sizeof(int));
      for (i = 0; i < nlocalverts; ++i) {
        int* offset_ptr = &pred_owner_offsets[pred[i] == -1 ? size - 1 : VERTEX_OWNER(pred[i])];
        preds_per_owner[*offset_ptr] = pred[i];
        preds_per_owner_results_offsets[*offset_ptr] = i;
        ++*offset_ptr;
      }
      for (r = 0; r < size; ++r) {
        assert (pred_owner_offsets[r] == pred_owner_displs[r + 1]);
      }
      free(pred_owner_offsets);

      /* Send around the number of vertices that will be sent to each destination. */
      int* num_my_preds_per_sender = (int*)xmalloc(size * sizeof(int));
      MPI_Alltoall(num_preds_per_owner, 1, MPI_INT,
                   num_my_preds_per_sender, 1, MPI_INT,
                   MPI_COMM_WORLD);
      int* my_preds_per_sender_displs = (int*)xmalloc((size + 1) * sizeof(int));
      my_preds_per_sender_displs[0] = 0;
      for (r = 0; r < size; ++r) {
        my_preds_per_sender_displs[r + 1] = my_preds_per_sender_displs[r] + num_my_preds_per_sender[r];
      }
      /* Send around the actual vertex data (list of depth requests that will
       * be responded to at each BFS iteration). */
      int64_t* my_depth_requests = (int64_t*)xmalloc(my_preds_per_sender_displs[size] * sizeof(int64_t));
      int64_t* my_depth_replies = (int64_t*)xmalloc(my_preds_per_sender_displs[size] * sizeof(int64_t));
      MPI_Alltoallv(preds_per_owner, num_preds_per_owner, pred_owner_displs, INT64_T_MPI_TYPE,
                    my_depth_requests, num_my_preds_per_sender, my_preds_per_sender_displs, INT64_T_MPI_TYPE,
                    MPI_COMM_WORLD);

      int64_t* pred_depth_raw = (int64_t*)xmalloc(nlocalverts * sizeof(int64_t)); /* Depth of predecessor vertex for each local vertex, ordered by source proc */

      /* Do a mini-BFS (naively) over just the predecessor graph (hopefully a
       * tree) produced by the real BFS; fill in the depth map. */
      while (1) {
        int any_changed = 0;
        int i;
        /* Create and send the depth values requested by other nodes.  The list
         * of requests is sent once, and are stored on the receiver so the
         * replies can be sent (possibly with updated depth values) at every
         * iteration. */
        for (i = 0; i < my_preds_per_sender_displs[size]; ++i) {
          my_depth_replies[i] = (my_depth_requests[i] == -1 ? INT64_MAX : depth[VERTEX_LOCAL(my_depth_requests[i])]);
        }
        MPI_Alltoallv(my_depth_replies, num_my_preds_per_sender, my_preds_per_sender_displs, INT64_T_MPI_TYPE,
                      pred_depth_raw, num_preds_per_owner, pred_owner_displs, INT64_T_MPI_TYPE,
                      MPI_COMM_WORLD);
        {
          size_t i;
          /* Put the received depths into the local array. */
          for (i = 0; i < nlocalverts; ++i) {
            pred_depth[preds_per_owner_results_offsets[i]] = pred_depth_raw[i];
          }
          /* Check those values to determine if they violate any correctness
           * conditions. */
          for (i = 0; i < nlocalverts; ++i) {
            int64_t v = VERTEX_TO_GLOBAL(i);
            if (v == root) {
              /* The depth and predecessor for this were checked earlier. */
            } else if (depth[i] == INT64_MAX && pred_depth[i] == INT64_MAX) {
              /* OK -- depth should be filled in later. */
            } else if (depth[i] == INT64_MAX && pred_depth[i] != INT64_MAX) {
              depth[i] = pred_depth[i] + 1;
              any_changed = 1;
            } else if (depth[i] != pred_depth[i] + 1) {
              fprintf(stderr, "%d: Validation error: BFS predecessors do not form a tree; see vertices %" PRId64 " (depth %" PRId64 ") and %" PRId64 " (depth %" PRId64 ").\n", rank, v, depth[i], pred[i], pred_depth[i]);
              validation_passed = 0;
            } else {
              /* Vertex already has its correct depth value. */
            }
          }
        }
        MPI_Allreduce(MPI_IN_PLACE, &any_changed, 1, MPI_INT, MPI_LOR, MPI_COMM_WORLD);
        if (!any_changed) break;
      }

      free(num_preds_per_owner);
      free(num_my_preds_per_sender);
      free(preds_per_owner);
      free(preds_per_owner_results_offsets);
      free(my_preds_per_sender_displs);
      free(my_depth_requests);
      free(my_depth_replies);
      free(pred_owner_displs);
      free(pred_depth);
      free(pred_depth_raw);
    }

    /* Check that all edges connect vertices whose depths differ by at most
     * one. */
    {
      int64_t maxlocaledges = 0;
      maxlocaledges = nlocaledges;
      MPI_Allreduce(MPI_IN_PLACE, &maxlocaledges, 1, INT64_T_MPI_TYPE, MPI_MAX, MPI_COMM_WORLD);
      /* We break the total list of overall edges into chunks to reduce the
       * amount of data to be sent at a time (since we are using MPI_Alltoallv
       * to send data collectively). */
      const int edge_chunk_size = (1 << 23); /* Reduce memory usage */
      int num_edge_groups = (maxlocaledges + edge_chunk_size - 1) / edge_chunk_size;
      int eg;
      for (eg = 0; eg < num_edge_groups; ++eg) {
        size_t first_edge_index = (size_t)(eg * edge_chunk_size);
        if (first_edge_index > nlocaledges) first_edge_index = nlocaledges;
        size_t last_edge_index = (size_t)((eg + 1) * edge_chunk_size);
        if (last_edge_index > nlocaledges) last_edge_index = nlocaledges;
        /* Sort the edge targets in this chunk by their owners (histogram
         * sort); see the BFS code above for details of the steps of the
         * algorithm. */
        int* num_edge_targets_by_owner = (int*)xcalloc(size, sizeof(int)); /* Uses zero-init */
        size_t ei;
        for (ei = first_edge_index; ei < last_edge_index; ++ei) {
          ++num_edge_targets_by_owner[VERTEX_OWNER(g->column[ei])];
        }
        int* edge_targets_by_owner_displs = (int*)xmalloc((size + 1) * sizeof(int));
        edge_targets_by_owner_displs[0] = 0;
        int i;
        for (i = 0; i < size; ++i) {
          edge_targets_by_owner_displs[i + 1] = edge_targets_by_owner_displs[i] + num_edge_targets_by_owner[i];
        }
        int64_t* edge_targets_by_owner = (int64_t*)xmalloc(edge_targets_by_owner_displs[size] * sizeof(int64_t));
        int64_t* edge_targets_by_owner_indices = (int64_t*)xmalloc(edge_targets_by_owner_displs[size] * sizeof(int64_t)); /* Source indices for where to write the targets */
        int* edge_targets_by_owner_offsets = (int*)xmalloc((size + 1) * sizeof(int));
        memcpy(edge_targets_by_owner_offsets, edge_targets_by_owner_displs, (size + 1) * sizeof(int));
        for (ei = first_edge_index; ei < last_edge_index; ++ei) {
          edge_targets_by_owner[edge_targets_by_owner_offsets[VERTEX_OWNER(g->column[ei])]] = g->column[ei];
          edge_targets_by_owner_indices[edge_targets_by_owner_offsets[VERTEX_OWNER(g->column[ei])]] = ei;
          ++edge_targets_by_owner_offsets[VERTEX_OWNER(g->column[ei])];
        }
        for (i = 0; i < size; ++i) {
          assert (edge_targets_by_owner_offsets[i] == edge_targets_by_owner_displs[i + 1]);
        }
        free(edge_targets_by_owner_offsets);

        /* Send around the number of data elements that will be sent later. */
        int* num_incoming_targets_by_src = (int*)xmalloc(size * sizeof(int));
        MPI_Alltoall(num_edge_targets_by_owner, 1, MPI_INT,
                     num_incoming_targets_by_src, 1, MPI_INT,
                     MPI_COMM_WORLD);
        int* incoming_targets_by_src_displs = (int*)xmalloc((size + 1) * sizeof(int));
        incoming_targets_by_src_displs[0] = 0;
        for (i = 0; i < size; ++i) {
          incoming_targets_by_src_displs[i + 1] = incoming_targets_by_src_displs[i] + num_incoming_targets_by_src[i];
        }

        int64_t* target_depth_requests = (int64_t*)xmalloc(incoming_targets_by_src_displs[size] * sizeof(int64_t));
        int64_t* target_depth_replies = (int64_t*)xmalloc(incoming_targets_by_src_displs[size] * sizeof(int64_t));

        /* Send the actual requests for the depths of edge targets. */
        MPI_Alltoallv(edge_targets_by_owner, num_edge_targets_by_owner, edge_targets_by_owner_displs, INT64_T_MPI_TYPE,
                      target_depth_requests, num_incoming_targets_by_src, incoming_targets_by_src_displs, INT64_T_MPI_TYPE,
                      MPI_COMM_WORLD);

        free(edge_targets_by_owner);

        /* Fill in the replies for the requests sent to me. */
        for (i = 0; i < incoming_targets_by_src_displs[size]; ++i) {
          assert (VERTEX_OWNER(target_depth_requests[i]) == rank);
          target_depth_replies[i] = depth[VERTEX_LOCAL(target_depth_requests[i])];
        }

        free(target_depth_requests);

        int64_t* target_depth_raw = (int64_t*)xmalloc((last_edge_index - first_edge_index) * sizeof(int64_t));

        /* Send back the replies. */
        MPI_Alltoallv(target_depth_replies, num_incoming_targets_by_src, incoming_targets_by_src_displs, INT64_T_MPI_TYPE,
                      target_depth_raw, num_edge_targets_by_owner, edge_targets_by_owner_displs, INT64_T_MPI_TYPE,
                      MPI_COMM_WORLD);

        free(target_depth_replies);
        free(num_incoming_targets_by_src);
        free(num_edge_targets_by_owner);
        free(incoming_targets_by_src_displs);
        free(edge_targets_by_owner_displs);

        int64_t* target_depth = (int64_t*)xmalloc((last_edge_index - first_edge_index) * sizeof(int64_t));

        /* Put the replies into the proper order (original order of the edges).
         * */
        for (ei = 0; ei < last_edge_index - first_edge_index; ++ei) {
          target_depth[edge_targets_by_owner_indices[ei] - first_edge_index] = target_depth_raw[ei];
        }

        free(target_depth_raw);
        free(edge_targets_by_owner_indices);

        /* Check the depth relationship of the endpoints of each edge in the
         * current chunk. */
        size_t src_i = 0;
        for (ei = first_edge_index; ei < last_edge_index; ++ei) {
          while (ei >= g->rowstarts[src_i + 1]) {
            ++src_i;
          }
          int64_t src = VERTEX_TO_GLOBAL(src_i);
          int64_t src_depth = depth[src_i];
          int64_t tgt = g->column[ei];
          int64_t tgt_depth = target_depth[ei - first_edge_index];
          if (src_depth != INT64_MAX && tgt_depth == INT64_MAX) {
            fprintf(stderr, "%d: Validation error: edge connects vertex %" PRId64 " in the BFS tree (depth %" PRId64 ") to vertex %" PRId64 " outside the tree.\n", rank, src, src_depth, tgt);
            validation_passed = 0;
          } else if (src_depth == INT64_MAX && tgt_depth != INT64_MAX) {
            /* Skip this for now; this problem will be caught when scanning
             * reversed copy of this edge.  Set the failure flag, though,
             * just in case. */
            validation_passed = 0;
          } else if (src_depth - tgt_depth < -1 ||
                     src_depth - tgt_depth > 1) {
            fprintf(stderr, "%d: Validation error: depths of edge endpoints %" PRId64 " (depth %" PRId64 ") and %" PRId64 " (depth %" PRId64 ") are too far apart (abs. val. > 1).\n", rank, src, src_depth, tgt, tgt_depth);
            validation_passed = 0;
          }
        }
        free(target_depth);
      }
    }

    free(depth);

  } /* End of part skipped by range errors */
  
  /* Collect the global validation result. */
  MPI_Allreduce(MPI_IN_PLACE, &validation_passed, 1, MPI_INT, MPI_LAND, MPI_COMM_WORLD);
  return validation_passed;
}
Example #24
0
static void
test_xcalloc_fail() {
  expect_string( mock_die, output, "Out of memory, xcalloc failed" );
  expect_assert_failure( xcalloc( 1, 1 ) );
}
Example #25
0
/*
 * To insert a leaf_node:
 * Search to the tree location appropriate for the given leaf_node's key:
 * - If location is unused (NULL), store the tweaked pointer directly there
 * - If location holds a note entry that matches the note-to-be-inserted, then
 *   combine the two notes (by calling the given combine_notes function).
 * - If location holds a note entry that matches the subtree-to-be-inserted,
 *   then unpack the subtree-to-be-inserted into the location.
 * - If location holds a matching subtree entry, unpack the subtree at that
 *   location, and restart the insert operation from that level.
 * - Else, create a new int_node, holding both the node-at-location and the
 *   node-to-be-inserted, and store the new int_node into the location.
 */
static int note_tree_insert(struct notes_tree *t, struct int_node *tree,
		unsigned char n, struct leaf_node *entry, unsigned char type,
		combine_notes_fn combine_notes)
{
	struct int_node *new_node;
	struct leaf_node *l;
	void **p = note_tree_search(t, &tree, &n, entry->key_sha1);
	int ret = 0;

	assert(GET_PTR_TYPE(entry) == 0); /* no type bits set */
	l = (struct leaf_node *) CLR_PTR_TYPE(*p);
	switch (GET_PTR_TYPE(*p)) {
	case PTR_TYPE_NULL:
		assert(!*p);
		if (is_null_sha1(entry->val_sha1))
			free(entry);
		else
			*p = SET_PTR_TYPE(entry, type);
		return 0;
	case PTR_TYPE_NOTE:
		switch (type) {
		case PTR_TYPE_NOTE:
			if (!hashcmp(l->key_sha1, entry->key_sha1)) {
				/* skip concatenation if l == entry */
				if (!hashcmp(l->val_sha1, entry->val_sha1))
					return 0;

				ret = combine_notes(l->val_sha1,
						    entry->val_sha1);
				if (!ret && is_null_sha1(l->val_sha1))
					note_tree_remove(t, tree, n, entry);
				free(entry);
				return ret;
			}
			break;
		case PTR_TYPE_SUBTREE:
			if (!SUBTREE_SHA1_PREFIXCMP(l->key_sha1,
						    entry->key_sha1)) {
				/* unpack 'entry' */
				load_subtree(t, entry, tree, n);
				free(entry);
				return 0;
			}
			break;
		}
		break;
	case PTR_TYPE_SUBTREE:
		if (!SUBTREE_SHA1_PREFIXCMP(entry->key_sha1, l->key_sha1)) {
			/* unpack 'l' and restart insert */
			*p = NULL;
			load_subtree(t, l, tree, n);
			free(l);
			return note_tree_insert(t, tree, n, entry, type,
						combine_notes);
		}
		break;
	}

	/* non-matching leaf_node */
	assert(GET_PTR_TYPE(*p) == PTR_TYPE_NOTE ||
	       GET_PTR_TYPE(*p) == PTR_TYPE_SUBTREE);
	if (is_null_sha1(entry->val_sha1)) { /* skip insertion of empty note */
		free(entry);
		return 0;
	}
	new_node = (struct int_node *) xcalloc(sizeof(struct int_node), 1);
	ret = note_tree_insert(t, new_node, n + 1, l, GET_PTR_TYPE(*p),
			       combine_notes);
	if (ret)
		return ret;
	*p = SET_PTR_TYPE(new_node, PTR_TYPE_INTERNAL);
	return note_tree_insert(t, new_node, n + 1, entry, type, combine_notes);
}
Example #26
0
static void
test_xcalloc_and_xfree() {
  void *mem = xcalloc( 1, 1 );
  assert_int_equal( 0, ( ( char * ) mem )[ 0 ] );
  xfree( mem );
}
Example #27
0
static void
kex_choose_conf(Kex *kex)
{
	Newkeys *newkeys;
	char **my, **peer;
	char **cprop, **sprop;
	int nenc, nmac, ncomp;
	u_int mode, ctos, need;
	int first_kex_follows, type;
#ifdef	NONE_CIPHER_ENABLED
	int auth_flag;
#endif

	my   = kex_buf2prop(&kex->my, NULL);
	peer = kex_buf2prop(&kex->peer, &first_kex_follows);

	if (kex->server) {
		cprop=peer;
		sprop=my;
	} else {
		cprop=my;
		sprop=peer;
	}

	/* Check whether server offers roaming */
	if (!kex->server) {
		char *roaming;
		roaming = match_list(KEX_RESUME, peer[PROPOSAL_KEX_ALGS], NULL);
		if (roaming) {
			kex->roaming = 1;
			xfree(roaming);
		}
	}

	/* Algorithm Negotiation */
#ifdef	NONE_CIPHER_ENABLED
	auth_flag = packet_get_authentication_state();
	debug ("AUTH STATE is %d", auth_flag);
#endif
	for (mode = 0; mode < MODE_MAX; mode++) {
		newkeys = xcalloc(1, sizeof(*newkeys));
		kex->newkeys[mode] = newkeys;
		ctos = (!kex->server && mode == MODE_OUT) ||
		    (kex->server && mode == MODE_IN);
		nenc  = ctos ? PROPOSAL_ENC_ALGS_CTOS  : PROPOSAL_ENC_ALGS_STOC;
		nmac  = ctos ? PROPOSAL_MAC_ALGS_CTOS  : PROPOSAL_MAC_ALGS_STOC;
		ncomp = ctos ? PROPOSAL_COMP_ALGS_CTOS : PROPOSAL_COMP_ALGS_STOC;
		choose_enc (&newkeys->enc,  cprop[nenc],  sprop[nenc]);
		choose_mac (&newkeys->mac,  cprop[nmac],  sprop[nmac]);
		choose_comp(&newkeys->comp, cprop[ncomp], sprop[ncomp]);
#ifdef	NONE_CIPHER_ENABLED
		debug("REQUESTED ENC.NAME is '%s'", newkeys->enc.name);
		if (strcmp(newkeys->enc.name, "none") == 0) {
			debug("Requesting NONE. Authflag is %d", auth_flag);			
			if (auth_flag == 1)
				debug("None requested post authentication.");
			else
				fatal("Pre-authentication none cipher requests "
				    "are not allowed.");
		} 
#endif
		debug("kex: %s %s %s %s",
		    ctos ? "client->server" : "server->client",
		    newkeys->enc.name,
		    newkeys->mac.name,
		    newkeys->comp.name);
	}
	choose_kex(kex, cprop[PROPOSAL_KEX_ALGS], sprop[PROPOSAL_KEX_ALGS]);
	choose_hostkeyalg(kex, cprop[PROPOSAL_SERVER_HOST_KEY_ALGS],
	    sprop[PROPOSAL_SERVER_HOST_KEY_ALGS]);
	need = 0;
	for (mode = 0; mode < MODE_MAX; mode++) {
		newkeys = kex->newkeys[mode];
		if (need < newkeys->enc.key_len)
			need = newkeys->enc.key_len;
		if (need < newkeys->enc.block_size)
			need = newkeys->enc.block_size;
		if (need < newkeys->mac.key_len)
			need = newkeys->mac.key_len;
	}
	/* XXX need runden? */
	kex->we_need = need;

	/* ignore the next message if the proposals do not match */
	if (first_kex_follows && !proposals_match(my, peer) &&
	    !(datafellows & SSH_BUG_FIRSTKEX)) {
		type = packet_read();
		debug2("skipping next packet (type %u)", type);
	}

	kex_prop_free(my);
	kex_prop_free(peer);
}
Example #28
0
void glp_mpl_build_prob(glp_tran *tran, glp_prob *prob)
{     /* build LP/MIP problem instance from the model */
      int m, n, i, j, t, kind, type, len, *ind;
      double lb, ub, *val;
      if (tran->phase != 3)
         xerror("glp_mpl_build_prob: invalid call sequence\n");
      /* erase the problem object */
      glp_erase_prob(prob);
      /* set problem name */
      glp_set_prob_name(prob, mpl_get_prob_name(tran));
      /* build rows (constraints) */
      m = mpl_get_num_rows(tran);
      if (m > 0)
         glp_add_rows(prob, m);
      for (i = 1; i <= m; i++)
      {  /* set row name */
         glp_set_row_name(prob, i, mpl_get_row_name(tran, i));
         /* set row bounds */
         type = mpl_get_row_bnds(tran, i, &lb, &ub);
         switch (type)
         {  case MPL_FR: type = GLP_FR; break;
            case MPL_LO: type = GLP_LO; break;
            case MPL_UP: type = GLP_UP; break;
            case MPL_DB: type = GLP_DB; break;
            case MPL_FX: type = GLP_FX; break;
            default: xassert(type != type);
         }
         if (type == GLP_DB && fabs(lb - ub) < 1e-9 * (1.0 + fabs(lb)))
         {  type = GLP_FX;
            if (fabs(lb) <= fabs(ub)) ub = lb; else lb = ub;
         }
         glp_set_row_bnds(prob, i, type, lb, ub);
         /* warn about non-zero constant term */
         if (mpl_get_row_c0(tran, i) != 0.0)
            xprintf("glp_mpl_build_prob: row %s; constant term %.12g ig"
               "nored\n",
               mpl_get_row_name(tran, i), mpl_get_row_c0(tran, i));
      }
      /* build columns (variables) */
      n = mpl_get_num_cols(tran);
      if (n > 0)
         glp_add_cols(prob, n);
      for (j = 1; j <= n; j++)
      {  /* set column name */
         glp_set_col_name(prob, j, mpl_get_col_name(tran, j));
         /* set column kind */
         kind = mpl_get_col_kind(tran, j);
         switch (kind)
         {  case MPL_NUM:
               break;
            case MPL_INT:
            case MPL_BIN:
               glp_set_col_kind(prob, j, GLP_IV);
               break;
            default:
               xassert(kind != kind);
         }
         /* set column bounds */
         type = mpl_get_col_bnds(tran, j, &lb, &ub);
         switch (type)
         {  case MPL_FR: type = GLP_FR; break;
            case MPL_LO: type = GLP_LO; break;
            case MPL_UP: type = GLP_UP; break;
            case MPL_DB: type = GLP_DB; break;
            case MPL_FX: type = GLP_FX; break;
            default: xassert(type != type);
         }
         if (kind == MPL_BIN)
         {  if (type == GLP_FR || type == GLP_UP || lb < 0.0) lb = 0.0;
            if (type == GLP_FR || type == GLP_LO || ub > 1.0) ub = 1.0;
            type = GLP_DB;
         }
         if (type == GLP_DB && fabs(lb - ub) < 1e-9 * (1.0 + fabs(lb)))
         {  type = GLP_FX;
            if (fabs(lb) <= fabs(ub)) ub = lb; else lb = ub;
         }
         glp_set_col_bnds(prob, j, type, lb, ub);
      }
      /* load the constraint matrix */
      ind = xcalloc(1+n, sizeof(int));
      val = xcalloc(1+n, sizeof(double));
      for (i = 1; i <= m; i++)
      {  len = mpl_get_mat_row(tran, i, ind, val);
         glp_set_mat_row(prob, i, len, ind, val);
      }
      /* build objective function (the first objective is used) */
      for (i = 1; i <= m; i++)
      {  kind = mpl_get_row_kind(tran, i);
         if (kind == MPL_MIN || kind == MPL_MAX)
         {  /* set objective name */
            glp_set_obj_name(prob, mpl_get_row_name(tran, i));
            /* set optimization direction */
            glp_set_obj_dir(prob, kind == MPL_MIN ? GLP_MIN : GLP_MAX);
            /* set constant term */
            glp_set_obj_coef(prob, 0, mpl_get_row_c0(tran, i));
            /* set objective coefficients */
            len = mpl_get_mat_row(tran, i, ind, val);
            for (t = 1; t <= len; t++)
               glp_set_obj_coef(prob, ind[t], val[t]);
            break;
         }
      }
      /* free working arrays */
      xfree(ind);
      xfree(val);
      return;
}
Example #29
0
/*--------------------------------------------------------------------*/
void profile_init(profile_t *p, u32 num_events) {

	p->num_events = num_events;
	p->total_time = -read_clock();
	p->events = (u64 *)xcalloc(num_events, sizeof(u64));
}
Example #30
-2
/*
 * Splits 's' into an argument vector. Handles quoted string and basic
 * escape characters (\\, \", \'). Caller must free the argument vector
 * and its members.
 */
static int
split_argv(const char *s, int *argcp, char ***argvp)
{
	int r = SSH_ERR_INTERNAL_ERROR;
	int argc = 0, quote, i, j;
	char *arg, **argv = xcalloc(1, sizeof(*argv));

	*argvp = NULL;
	*argcp = 0;

	for (i = 0; s[i] != '\0'; i++) {
		/* Skip leading whitespace */
		if (s[i] == ' ' || s[i] == '\t')
			continue;

		/* Start of a token */
		quote = 0;
		if (s[i] == '\\' &&
		    (s[i + 1] == '\'' || s[i + 1] == '\"' || s[i + 1] == '\\'))
			i++;
		else if (s[i] == '\'' || s[i] == '"')
			quote = s[i++];

		argv = xreallocarray(argv, (argc + 2), sizeof(*argv));
		arg = argv[argc++] = xcalloc(1, strlen(s + i) + 1);
		argv[argc] = NULL;

		/* Copy the token in, removing escapes */
		for (j = 0; s[i] != '\0'; i++) {
			if (s[i] == '\\') {
				if (s[i + 1] == '\'' ||
				    s[i + 1] == '\"' ||
				    s[i + 1] == '\\') {
					i++; /* Skip '\' */
					arg[j++] = s[i];
				} else {
					/* Unrecognised escape */
					arg[j++] = s[i];
				}
			} else if (quote == 0 && (s[i] == ' ' || s[i] == '\t'))
				break; /* done */
			else if (quote != 0 && s[i] == quote)
				break; /* done */
			else
				arg[j++] = s[i];
		}
		if (s[i] == '\0') {
			if (quote != 0) {
				/* Ran out of string looking for close quote */
				r = SSH_ERR_INVALID_FORMAT;
				goto out;
			}
			break;
		}
	}
	/* Success */
	*argcp = argc;
	*argvp = argv;
	argc = 0;
	argv = NULL;
	r = 0;
 out:
	if (argc != 0 && argv != NULL) {
		for (i = 0; i < argc; i++)
			free(argv[i]);
		free(argv);
	}
	return r;
}