예제 #1
0
파일: race.c 프로젝트: abustany/go
void
runtime·raceread(uintptr addr)
{
	if(!onstack(addr)) {
		m->racecall = true;
		runtime∕race·Read(g->racectx, (void*)addr, runtime·getcallerpc(&addr));
		m->racecall = false;
	}
}
예제 #2
0
파일: race.c 프로젝트: icattlecoder/go
void
runtime·racewrite(uintptr addr)
{
	if(!onstack(addr)) {
		m->racecall = true;
		runtime∕race·Write(g->goid-1, (void*)addr, runtime·getcallerpc(&addr));
		m->racecall = false;
	}
}
예제 #3
0
파일: race.c 프로젝트: blackbeans/golang
static void
rangeaccess(void *addr, uintptr size, uintptr step, uintptr callpc, uintptr pc, bool write)
{
	uintptr racectx;

	if(!onstack((uintptr)addr)) {
		m->racecall = true;
		racectx = g->racectx;
		if(callpc) {
			if(callpc == (uintptr)runtime·lessstack)
				runtime·callers(3, &callpc, 1);
			runtime∕race·FuncEnter(racectx, (void*)callpc);
		}
		if(write)
			runtime∕race·WriteRange(racectx, addr, size, step, (void*)pc);
		else
			runtime∕race·ReadRange(racectx, addr, size, step, (void*)pc);
		if(callpc)
			runtime∕race·FuncExit(racectx);
		m->racecall = false;
	}
}
예제 #4
0
파일: race.c 프로젝트: icattlecoder/go
static void
memoryaccess(void *addr, uintptr callpc, uintptr pc, bool write)
{
	int64 goid;

	if(!onstack((uintptr)addr)) {
		m->racecall = true;
		goid = g->goid-1;
		if(callpc) {
			if(callpc == (uintptr)runtime·lessstack ||
				(callpc >= (uintptr)runtime·mheap.arena_start && callpc < (uintptr)runtime·mheap.arena_used))
				runtime·callers(3, &callpc, 1);
			runtime∕race·FuncEnter(goid, (void*)callpc);
		}
		if(write)
			runtime∕race·Write(goid, addr, (void*)pc);
		else
			runtime∕race·Read(goid, addr, (void*)pc);
		if(callpc)
			runtime∕race·FuncExit(goid);
		m->racecall = false;
	}
}
예제 #5
0
static int
get_info(efi_guid_t *guid, uint64_t hw_inst, update_info **info)
{
	efi_guid_t varguid = FWUPDATE_GUID;
	char *varname = NULL;
	char *guidstr = NULL;
	int rc;
	update_info *local;
	int error;

	rc = efi_guid_to_str(guid, &guidstr);
	if (rc < 0)
		return -1;
	guidstr = onstack(guidstr, strlen(guidstr)+1);

	rc = asprintf(&varname, "fwupdate-%s-%"PRIx64, guidstr, hw_inst);
	if (rc < 0)
		return -1;
	varname = onstack(varname, strlen(varname)+1);

	uint8_t *data = NULL;
	size_t data_size = 0;
	uint32_t attributes;

	rc = efi_get_variable(varguid, varname, &data, &data_size, &attributes);
	if (rc < 0) {
		if (errno != ENOENT)
			return -1;
		local = calloc(1, sizeof (*local));
		if (!local)
			return -1;

		local->update_info_version = UPDATE_INFO_VERSION;
		local->guid = *guid;
		local->hw_inst = hw_inst;

		local->dp_ptr = calloc(1, 1024);
		if (!local->dp_ptr) {
alloc_err:
			error = errno;
			free_info(local);
			errno = error;
			return -1;
		}

		ssize_t sz;
		sz = efidp_make_end_entire((uint8_t *)local->dp_ptr, 1024);
		if (sz < 0) {
			rc = sz;
			goto alloc_err;
		}
		*info = local;
		return 0;
	}

	/* If our size is wrong, or our data is otherwise bad, try to delete
	 * the variable and create a new one. */
	if (data_size < sizeof (*local) || !data) {
		if (data)
			free(data);
get_err:
		rc = efi_del_variable(varguid, varname);
		if (rc < 0)
			return -1;
		return get_info(guid, hw_inst, info);
	}
	local = (update_info *)data;

	if (local->update_info_version != UPDATE_INFO_VERSION)
		goto get_err;

	ssize_t sz = efidp_size((efidp)local->dp);
	if (sz < 0) {
		free(data);
		errno = EINVAL;
		return -1;
	}

	efidp_header *dp = malloc((size_t)sz);
	if (!dp) {
		free(data);
		errno = ENOMEM;
		return -1;
	}

	memcpy(dp, local->dp, (size_t)sz);
	local->dp_ptr = dp;

	*info = local;
	return 0;
}