⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 dt_consume.c

📁 Sun Solaris 10 中的 DTrace 组件的源代码。请参看: http://www.sun.com/software/solaris/observability.jsp
💻 C
📖 第 1 页 / 共 3 页
字号:
	for (i = 0; i < depth && pc[i] != NULL; i++) {		if ((err = dt_printf(dtp, fp, "%*s", indent, "")) < 0)			break;		if (P != NULL && Plookup_by_addr(P, pc[i],		    name, sizeof (name), &sym) == 0) {			(void) Pobjname(P, pc[i], objname, sizeof (objname));			if (pc[i] > sym.st_value) {				(void) snprintf(c, sizeof (c),				    "%s`%s+0x%llx", dt_basename(objname), name,				    (u_longlong_t)(pc[i] - sym.st_value));			} else {				(void) snprintf(c, sizeof (c),				    "%s`%s", dt_basename(objname), name);			}		} else if (str != NULL && str[0] != '\0') {			(void) snprintf(c, sizeof (c), "%s", str);		} else {			if (P != NULL && Pobjname(P, pc[i], objname,			    sizeof (objname)) != NULL) {				(void) snprintf(c, sizeof (c), "%s`0x%llx",				    dt_basename(objname), (u_longlong_t)pc[i]);			} else {				(void) snprintf(c, sizeof (c), "0x%llx",				    (u_longlong_t)pc[i]);			}		}		if (err < 0)			break;		if (dt_printf(dtp, fp, format, c) < 0)			return (-1);		if (dt_printf(dtp, fp, "\n") < 0)			return (-1);		if (str != NULL) {			str += strlen(str) + 1;			if (str - strbase >= strsize)				str = NULL;		}	}	if (P != NULL) {		dt_proc_unlock(dtp, P);		dt_proc_release(dtp, P);	}	return (err);}typedef struct dt_normal {	dtrace_aggvarid_t dtnd_id;	uint64_t dtnd_normal;} dt_normal_t;static intdt_normalize_agg(dtrace_aggdata_t *aggdata, void *arg){	dt_normal_t *normal = arg;	dtrace_aggdesc_t *agg = aggdata->dtada_desc;	dtrace_aggvarid_t id = normal->dtnd_id;	uintptr_t data = (uintptr_t)aggdata->dtada_data;	if (agg->dtagd_nrecs == 0)		return (DTRACE_AGGWALK_NEXT);	if (id != *(dtrace_aggvarid_t *)(data + agg->dtagd_rec[0].dtrd_offset))		return (DTRACE_AGGWALK_NEXT);	aggdata->dtada_normal = normal->dtnd_normal;	return (DTRACE_AGGWALK_NORMALIZE);}static intdt_normalize(dtrace_hdl_t *dtp, caddr_t base, dtrace_recdesc_t *rec){	dt_normal_t normal;	caddr_t addr;	/*	 * We (should) have two records:  the aggregation ID followed by the	 * normalization value.	 */	addr = base + rec->dtrd_offset;	if (rec->dtrd_size != sizeof (dtrace_aggvarid_t))		return (dt_set_errno(dtp, EDT_BADNORMAL));	/* LINTED - alignment */	normal.dtnd_id = *((dtrace_aggvarid_t *)addr);	rec++;	if (rec->dtrd_action != DTRACEACT_LIBACT)		return (dt_set_errno(dtp, EDT_BADNORMAL));	if (rec->dtrd_arg != DT_ACT_NORMALIZE)		return (dt_set_errno(dtp, EDT_BADNORMAL));	addr = base + rec->dtrd_offset;	switch (rec->dtrd_size) {	case sizeof (uint64_t):		/* LINTED - alignment */		normal.dtnd_normal = *((uint64_t *)addr);		break;	case sizeof (uint32_t):		/* LINTED - alignment */		normal.dtnd_normal = *((uint32_t *)addr);		break;	case sizeof (uint16_t):		/* LINTED - alignment */		normal.dtnd_normal = *((uint16_t *)addr);		break;	case sizeof (uint8_t):		normal.dtnd_normal = *((uint8_t *)addr);		break;	default:		return (dt_set_errno(dtp, EDT_BADNORMAL));	}	(void) dtrace_aggregate_walk(dtp, dt_normalize_agg, &normal);	return (0);}static intdt_denormalize_agg(dtrace_aggdata_t *aggdata, void *arg){	dtrace_aggdesc_t *agg = aggdata->dtada_desc;	dtrace_aggvarid_t id = *((dtrace_aggvarid_t *)arg);	uintptr_t data = (uintptr_t)aggdata->dtada_data;	if (agg->dtagd_nrecs == 0)		return (DTRACE_AGGWALK_NEXT);	if (id != *(dtrace_aggvarid_t *)(data + agg->dtagd_rec[0].dtrd_offset))		return (DTRACE_AGGWALK_NEXT);	return (DTRACE_AGGWALK_DENORMALIZE);}static intdt_clear_agg(dtrace_aggdata_t *aggdata, void *arg){	dtrace_aggdesc_t *agg = aggdata->dtada_desc;	dtrace_aggvarid_t id = *((dtrace_aggvarid_t *)arg);	uintptr_t data = (uintptr_t)aggdata->dtada_data;	if (agg->dtagd_nrecs == 0)		return (DTRACE_AGGWALK_NEXT);	if (id != *(dtrace_aggvarid_t *)(data + agg->dtagd_rec[0].dtrd_offset))		return (DTRACE_AGGWALK_NEXT);	return (DTRACE_AGGWALK_CLEAR);}typedef struct dt_trunc {	dtrace_aggvarid_t dttd_id;	uint64_t dttd_remaining;} dt_trunc_t;static intdt_trunc_agg(dtrace_aggdata_t *aggdata, void *arg){	dt_trunc_t *trunc = arg;	dtrace_aggdesc_t *agg = aggdata->dtada_desc;	dtrace_aggvarid_t id = trunc->dttd_id;	uintptr_t data = (uintptr_t)aggdata->dtada_data;	if (agg->dtagd_nrecs == 0)		return (DTRACE_AGGWALK_NEXT);	if (id != *(dtrace_aggvarid_t *)(data + agg->dtagd_rec[0].dtrd_offset))		return (DTRACE_AGGWALK_NEXT);	if (trunc->dttd_remaining == 0)		return (DTRACE_AGGWALK_REMOVE);	trunc->dttd_remaining--;	return (DTRACE_AGGWALK_NEXT);}static intdt_trunc(dtrace_hdl_t *dtp, caddr_t base, dtrace_recdesc_t *rec){	dt_trunc_t trunc;	caddr_t addr;	int64_t remaining;	int (*func)(dtrace_hdl_t *, dtrace_aggregate_f *, void *);	/*	 * We (should) have two records:  the aggregation ID followed by the	 * number of aggregation entries after which the aggregation is to be	 * truncated.	 */	addr = base + rec->dtrd_offset;	if (rec->dtrd_size != sizeof (dtrace_aggvarid_t))		return (dt_set_errno(dtp, EDT_BADTRUNC));	/* LINTED - alignment */	trunc.dttd_id = *((dtrace_aggvarid_t *)addr);	rec++;	if (rec->dtrd_action != DTRACEACT_LIBACT)		return (dt_set_errno(dtp, EDT_BADTRUNC));	if (rec->dtrd_arg != DT_ACT_TRUNC)		return (dt_set_errno(dtp, EDT_BADTRUNC));	addr = base + rec->dtrd_offset;	switch (rec->dtrd_size) {	case sizeof (uint64_t):		/* LINTED - alignment */		remaining = *((int64_t *)addr);		break;	case sizeof (uint32_t):		/* LINTED - alignment */		remaining = *((int32_t *)addr);		break;	case sizeof (uint16_t):		/* LINTED - alignment */		remaining = *((int16_t *)addr);		break;	case sizeof (uint8_t):		remaining = *((int8_t *)addr);		break;	default:		return (dt_set_errno(dtp, EDT_BADNORMAL));	}	if (remaining < 0) {		func = dtrace_aggregate_walk_valsorted;		remaining = -remaining;	} else {		func = dtrace_aggregate_walk_valrevsorted;	}	assert(remaining >= 0);	trunc.dttd_remaining = remaining;	(void) func(dtp, dt_trunc_agg, &trunc);	return (0);}intdt_print_agg(dtrace_aggdata_t *aggdata, void *arg){	int i, err = 0;	dt_print_aggdata_t *pd = arg;	dtrace_aggdesc_t *agg = aggdata->dtada_desc;	FILE *fp = pd->dtpa_fp;	dtrace_hdl_t *dtp = pd->dtpa_dtp;	dtrace_aggvarid_t aggvarid = pd->dtpa_id;	uintptr_t data = (uintptr_t)aggdata->dtada_data;	if (pd->dtpa_allunprint) {		if (agg->dtagd_flags & DTRACE_AGD_PRINTED)			return (0);	} else {		/*		 * If we're not printing all unprinted aggregations, then the		 * aggregation variable ID denotes a specific aggregation		 * variable that we should print -- skip any other aggregations		 * that we encounter.		 */		if (agg->dtagd_nrecs == 0)			return (0);		if (aggvarid != *(dtrace_aggvarid_t *)(data +		    agg->dtagd_rec[0].dtrd_offset))			return (0);	}	/*	 * Iterate over each record description, printing the traced data,	 * skipping the first datum (the tuple member created by the compiler).	 */	for (i = 1; err >= 0 && i < agg->dtagd_nrecs; i++) {		dtrace_recdesc_t *rec = &agg->dtagd_rec[i];		dtrace_actkind_t act = rec->dtrd_action;		caddr_t addr = aggdata->dtada_data + rec->dtrd_offset;		size_t size = rec->dtrd_size;		uint64_t normal;		normal = DTRACEACT_ISAGG(act) ? aggdata->dtada_normal : 1;		if (act == DTRACEACT_STACK) {			int depth = rec->dtrd_size / sizeof (pc_t);			err = dt_print_stack(dtp, fp, NULL, addr, depth);			goto nextrec;		}		if (act == DTRACEACT_USTACK || act == DTRACEACT_JSTACK) {			err = dt_print_ustack(dtp, fp, NULL, addr,			    rec->dtrd_arg);			goto nextrec;		}		if (act == DTRACEAGG_QUANTIZE) {			err = dt_print_quantize(dtp, fp, addr, size, normal);			goto nextrec;		}		if (act == DTRACEAGG_LQUANTIZE) {			err = dt_print_lquantize(dtp, fp, addr, size, normal);			goto nextrec;		}		if (act == DTRACEAGG_AVG) {			err = dt_print_average(dtp, fp, addr, size, normal);			goto nextrec;		}		switch (size) {		case sizeof (uint64_t):			err = dt_printf(dtp, fp, " %16lld",			    /* LINTED - alignment */			    (long long)*((uint64_t *)addr) / normal);			break;		case sizeof (uint32_t):			/* LINTED - alignment */			err = dt_printf(dtp, fp, " %8d", *((uint32_t *)addr) /			    (uint32_t)normal);			break;		case sizeof (uint16_t):			/* LINTED - alignment */			err = dt_printf(dtp, fp, " %5d", *((uint16_t *)addr) /			    (uint32_t)normal);			break;		case sizeof (uint8_t):			err = dt_printf(dtp, fp, " %3d", *((uint8_t *)addr) /			    (uint32_t)normal);			break;		default:			err = dt_print_bytes(dtp, fp, addr, size, 50, 0);			break;		}nextrec:		if (dt_buffered_flush(dtp, NULL, rec, aggdata) < 0)			return (-1);	}	if (err >= 0)		err = dt_printf(dtp, fp, "\n");	if (dt_buffered_flush(dtp, NULL, NULL, aggdata) < 0)		return (-1);	if (!pd->dtpa_allunprint)		agg->dtagd_flags |= DTRACE_AGD_PRINTED;	return (err < 0 ? -1 : 0);}static intdt_consume_cpu(dtrace_hdl_t *dtp, FILE *fp, int cpu, dtrace_bufdesc_t *buf,    dtrace_consume_probe_f *efunc, dtrace_consume_rec_f *rfunc, void *arg){	dtrace_epid_t id;	size_t offs, start = buf->dtbd_oldest, end = buf->dtbd_size;	int flow = (dtp->dt_options[DTRACEOPT_FLOWINDENT] != DTRACEOPT_UNSET);	int quiet = (dtp->dt_options[DTRACEOPT_QUIET] != DTRACEOPT_UNSET);	int rval, i, n;	dtrace_epid_t last = DTRACE_EPIDNONE;	dtrace_probedata_t data;	uint64_t drops;	caddr_t addr;	bzero(&data, sizeof (data));	data.dtpda_handle = dtp;	data.dtpda_cpu = cpu;again:	for (offs = start; offs < end; ) {		dtrace_eprobedesc_t *epd;		/*		 * We're guaranteed to have an ID.		 */		id = *(uint32_t *)((uintptr_t)buf->dtbd_data + offs);		if (id == DTRACE_EPIDNONE) {			/*			 * This is filler to assure proper alignment of the			 * next record; we simply ignore it.			 */			offs += sizeof (id);			continue;		}		if ((rval = dt_epid_lookup(dtp, id, &data.dtpda_edesc,		    &data.dtpda_pdesc)) != 0)			return (rval);		epd = data.dtpda_edesc;		data.dtpda_data = buf->dtbd_data + offs;		if (data.dtpda_edesc->dtepd_uarg != DT_ECB_DEFAULT) {			rval = dt_handle(dtp, &data);			if (rval == DTRACE_CONSUME_NEXT)				goto nextepid;			if (rval == DTRACE_CONSUME_ERROR)				return (-1);		}		if (flow)			(void) dt_flowindent(dtp, &data, last, buf, offs);		rval = (*efunc)(&data, arg);		if (flow) {			if (data.dtpda_flow == DTRACEFLOW_ENTRY)				data.dtpda_indent += 2;		}		if (rval == DTRACE_CONSUME_NEXT)			goto nextepid;		if (rval == DTRACE_CONSUME_ABORT)			return (dt_set_errno(dtp, EDT_DIRABORT));		if (rval != DTRACE_CONSUME_THIS)			return (dt_set_errno(dtp, EDT_BADRVAL));		for (i = 0; i < epd->dtepd_nrecs; i++) {			dtrace_recdesc_t *rec = &epd->dtepd_rec[i];			dtrace_actkind_t act = rec->dtrd_action;			data.dtpda_data = buf->dtbd_data + offs +			    rec->dtrd_offset;			addr = data.dtpda_data;			if (act == DTRACEACT_LIBACT) {				if (rec->dtrd_arg == DT_ACT_CLEAR) {					dtrace_aggvarid_t id;					/* LINTED - alignment */					id = *((dtrace_aggvarid_t *)addr);					(void) dtrace_aggregate_walk(dtp,					    dt_clear_agg, &id);					continue;				}				if (rec->dtrd_arg == DT_ACT_DENORMALIZE) {					dtrace_aggvarid_t id;					/* LINTED - alignment */					id = *((dtrace_aggvarid_t *)addr);					(void) dtrace_aggregate_walk(dtp,					    dt_denormalize_agg, &id);					continue;				}				if (rec->dtrd_arg == DT_ACT_NORMALIZE) {					if (i == epd->dtepd_nrecs - 1)						return (dt_set_errno(dtp,						    EDT_BADNORMAL));

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -