Пример #1
0
size_t os_fread_mbs(FILE *file, char **pstr)
{
	size_t size = 0;
	size_t len = 0;

	fseek(file, 0, SEEK_END);
	size = (size_t)os_ftelli64(file);
	*pstr = NULL;

	if (size > 0) {
		char *mbstr = bmalloc(size+1);

		fseek(file, 0, SEEK_SET);
		size = fread(mbstr, 1, size, file);
		if (size == 0) {
			bfree(mbstr);
			return 0;
		}

		mbstr[size] = 0;
		len = os_mbs_to_utf8_ptr(mbstr, size, pstr);
		bfree(mbstr);
	}

	return len;
}
Пример #2
0
int64_t os_fgetsize(FILE *file)
{
	int64_t cur_offset = os_ftelli64(file);
	int64_t size;
	int errval = 0;

	if (fseek(file, 0, SEEK_END) == -1)
		return -1;

	size = os_ftelli64(file);
	if (size == -1)
		errval = errno;

	if (os_fseeki64(file, cur_offset, SEEK_SET) != 0 && errval != 0)
		errno = errval;

	return size;
}
Пример #3
0
static void flv_output_stop(void *data)
{
	struct flv_output *stream = data;

	if (stream->active) {
		if (stream->file)
			write_file_info(stream->file, stream->last_packet_ts,
					os_ftelli64(stream->file));

		fclose(stream->file);
		obs_output_end_data_capture(stream->output);
		stream->active = false;
		stream->sent_headers = false;

		info("FLV file output complete");
	}
}
Пример #4
0
size_t os_fread_utf8(FILE *file, char **pstr)
{
	size_t size = 0;
	size_t len = 0;

	*pstr = NULL;

	fseek(file, 0, SEEK_END);
	size = (size_t)os_ftelli64(file);

	if (size > 0) {
		char bom[3];
		char *utf8str;
		off_t offset;

		bom[0] = 0;
		bom[1] = 0;
		bom[2] = 0;

		/* remove the ghastly BOM if present */
		fseek(file, 0, SEEK_SET);
		fread(bom, 1, 3, file);

		offset = (astrcmp_n(bom, "\xEF\xBB\xBF", 3) == 0) ? 3 : 0;

		size -= offset;
		if (size == 0)
			return 0;

		utf8str = bmalloc(size+1);
		fseek(file, offset, SEEK_SET);

		size = fread(utf8str, 1, size, file);
		if (size == 0) {
			bfree(utf8str);
			return 0;
		}

		utf8str[size] = 0;

		*pstr = utf8str;
	}

	return len;
}
Пример #5
0
static bool init_animated_gif(gs_image_file_t *image, const char *path)
{
	bool is_animated_gif = true;
	gif_result result;
	uint64_t max_size;
	size_t size;
	FILE *file;

	image->bitmap_callbacks.bitmap_create = bi_def_bitmap_create;
	image->bitmap_callbacks.bitmap_destroy = bi_def_bitmap_destroy;
	image->bitmap_callbacks.bitmap_get_buffer = bi_def_bitmap_get_buffer;
	image->bitmap_callbacks.bitmap_modified = bi_def_bitmap_modified;
	image->bitmap_callbacks.bitmap_set_opaque = bi_def_bitmap_set_opaque;
	image->bitmap_callbacks.bitmap_test_opaque = bi_def_bitmap_test_opaque;

	gif_create(&image->gif, &image->bitmap_callbacks);

	file = os_fopen(path, "rb");
	if (!file) {
		blog(LOG_WARNING, "Failed to open file '%s'", path);
		goto fail;
	}

	fseek(file, 0, SEEK_END);
	size = (size_t)os_ftelli64(file);
	fseek(file, 0, SEEK_SET);

	image->gif_data = bmalloc(size);
	fread(image->gif_data, 1, size, file);

	do {
		result = gif_initialise(&image->gif, size, image->gif_data);
		if (result < 0) {
			blog(LOG_WARNING, "Failed to initialize gif '%s', "
					"possible file corruption", path);
			goto fail;
		}
	} while (result != GIF_OK);

	if (image->gif.width > 4096 || image->gif.height > 4096) {
		blog(LOG_WARNING, "Bad texture dimensions (%dx%d) in '%s'",
				image->gif.width, image->gif.height, path);
		goto fail;
	}

	max_size = (uint64_t)image->gif.width * (uint64_t)image->gif.height *
		(uint64_t)image->gif.frame_count * 4LLU;

	if ((uint64_t)get_full_decoded_gif_size(image) != max_size) {
		blog(LOG_WARNING, "Gif '%s' overflowed maximum pointer size",
				path);
		goto fail;
	}

	image->is_animated_gif = (image->gif.frame_count > 1 && result >= 0);
	if (image->is_animated_gif) {
		gif_decode_frame(&image->gif, 0);

		image->animation_frame_cache = bzalloc(
				image->gif.frame_count * sizeof(uint8_t*));
		image->animation_frame_data = bzalloc(
				get_full_decoded_gif_size(image));

		for (unsigned int i = 0; i < image->gif.frame_count; i++) {
			if (gif_decode_frame(&image->gif, i) != GIF_OK)
				blog(LOG_WARNING, "Couldn't decode frame %u "
						"of '%s'", i, path);
		}

		gif_decode_frame(&image->gif, 0);

		image->cx = (uint32_t)image->gif.width;
		image->cy = (uint32_t)image->gif.height;
		image->format = GS_RGBA;
	} else {
		gif_finalise(&image->gif);
		bfree(image->gif_data);
		image->gif_data = NULL;
		is_animated_gif = false;
		goto not_animated;
	}

	image->loaded = true;

fail:
	if (!image->loaded)
		gs_image_file_free(image);
not_animated:
	if (file)
		fclose(file);

	return is_animated_gif;
}