Ejemplo n.º 1
0
void write_frame()
{
	int result = 0;
	int i;

// Shift data into frame buffer
	frame_buffer_size = frame_end - buffer;
	memcpy(frame_buffer, buffer, frame_buffer_size);





/*
 * if(
 * buffer[0] == 0xc2 &&
 * buffer[1] == 0x5c &&
 * buffer[2] == 0x43 &&
 * buffer[3] == 0x49 &&
 * buffer[4] == 0x95 &&
 * buffer[5] == 0xc4 &&
 * buffer[6] == 0xa6 &&
 * buffer[7] == 0x2b)
 * printf("write_frame %d\n", __LINE__);
 */

// Shift input buffer
	buffer_size = end - frame_end;
	memcpy(buffer, frame_end, buffer_size);

// Seek to end of this NAL
	ptr -= (frame_end - buffer);
	end = buffer + buffer_size;

	if(!frame_buffer_size) return;




/*
 * static int debug_count = 0;
 * char string[1024];
 * sprintf(string, "test%06d", debug_count++);
 * printf("write_frame %d: %s\n", __LINE__, string);
 * FILE *test = fopen(string, "w");
 * fwrite(frame_buffer, frame_buffer_size, 1, test);
 * fclose(test);
 */


	
	int got_picture = 0;
	AVFrame picture;


// Skip frames until first keyframe
/*
 * 	if(!bytes_written && !is_keyframe)
 * 	{
 * 	}
 * 	else
 */
	if(pass == 0)
	{
// Decode header only

printf("write_frame %d pass=%d %d\n", __LINE__, pass, frame_buffer_size);

/*
* static FILE *test = 0;
* if(!test) test = fopen("test", "w");
* fwrite(buffer, output_size, 1, test);
*/

		avcodec_get_frame_defaults(&picture);
		avcodec_decode_video(decoder_context, 
			&picture, 
			&got_picture, 
			buffer, 
			frame_buffer_size);


printf("write_frame %d %d\n", __LINE__, frame_buffer_size);


		if(decoder_context->width > 0)
		{
			video_width = decoder_context->width;
			video_height = decoder_context->height;
			video_frame_rate = (double)decoder_context->time_base.den / 
				decoder_context->time_base.num / 
				2;
			got_header = 1;
printf("%s format:\nwidth=%d\nheight=%d\nframerate=%f\naudio_track=%d\nsamplerate=%d\nchannels=%d\n", 
in_path,
video_width, 
video_height,
video_frame_rate,
audio_track,
audio_samplerate,
audio_channels);
		}

	}
	else
	{
/*
* printf("write_frame: %s at offset %llx\n", 
* is_keyframe ? "Keyframe" : "Frame", 
* bytes_written);
*/
		if(!quicktime_fd)
		{
			quicktime_fd = quicktime_open(out_path, 0, 1);
			if(!quicktime_fd)
			{
				fprintf(stderr, 
					"write_frame: Failed to open %s for writing\n",
					out_path);
				exit(1);
			}

#ifdef ENCODE_AUDIO
			quicktime_set_audio(quicktime_fd, 
				audio_channels, 
				audio_samplerate, 
				16, 
				QUICKTIME_MP4A);
			quicktime_set_parameter(quicktime_fd, "mp4a_bitrate", &audio_bitrate);
#endif

			quicktime_set_video(quicktime_fd, 
				1, 
				video_width, 
				video_height,
				video_frame_rate,
				QUICKTIME_H264);
		}



// Convert NAL codes to AVC format
		unsigned char *ptr2 = frame_buffer + NAL_CODE_SIZE;
		unsigned char *end2 = frame_buffer + frame_buffer_size;
		unsigned char *last_start = frame_buffer;
		int nal_size;
		int total_nals = 1;
		while(ptr2 < end2 + NAL_CODE_SIZE)
		{
// Start of next NAL code
			if(ptr2[0] == 0x00 &&
				ptr2[1] == 0x00 &&
				ptr2[2] == 0x00 &&
				ptr2[3] == 0x01)
			{
				nal_size = ptr2 - last_start - 4;
				last_start[0] = (nal_size & 0xff000000) >> 24;
				last_start[1] = (nal_size & 0xff0000) >> 16;
				last_start[2] = (nal_size & 0xff00) >> 8;
				last_start[3] = (nal_size & 0xff);
				last_start = ptr2;
				ptr2 += 4;
				total_nals++;
			}
			else
				ptr2++;
		}
Ejemplo n.º 2
0
int main(int argc, char *argv[])
{
	int error = 0;
	int frame_count = -1;
	char *row_pointers[3];
	int do_audio = 0;
	int do_video = 0;
	int channels = 0;
	long afragment = 65536;
	float **audio_output;
	int layer = 0;
	int astream = 0;
	char input_path[1024];
	char output_path[1024];
	int i;
	long current_frame = 0;
	long current_sample = 0;

	pthread_mutex_init(&mutex, NULL);
	signal(SIGINT, trap_interrupt);

	input_path[0] = 0;
	output_path[0] = 0;

	if(argc < 3)
	{
		printf("Usage: %s [-a] [-v] <mpeg file> <output movie> [frame count]\n", argv[0]);
		exit(1);
	}

	for(i = 1; i < argc; i++)
	{
		if(!strcmp(argv[i], "-a"))
		{
			do_audio = 1;
		}
		else
		if(!strcmp(argv[i], "-v"))
		{
			do_video = 1;
		}
		else
		if(!input_path[0])
		{
			strcpy(input_path, argv[i]);
		}
		else
		if(!output_path[0])
		{
			strcpy(output_path, argv[i]);
		}
		else
			frame_count = atol(argv[i]);
	}

//printf("main 1\n");
	if(!(input = mpeg3_open(input_path, &error)))
	{
		exit(1);
	}
//printf("main 1\n");

	if(!(output = quicktime_open(output_path, 0, 1)))
	{
		exit(1);
	}
//printf("main 1\n");

	if(do_video)
	{
		if(!mpeg3_total_vstreams(input))
		{
			do_video = 0;
		}
		else
		{
			quicktime_set_video(output, 
				1, 
				mpeg3_video_width(input, layer), 
				mpeg3_video_height(input, layer), 
				mpeg3_frame_rate(input, layer), 
				VIDEO_CODEC);
			quicktime_set_jpeg(output, 80, 0);
		}
	}
//printf("main 1\n");

	if(do_audio)
	{
		if(!mpeg3_total_astreams(input))
		{
			do_audio = 0;
		}
		else
		{
			int i;
			channels = mpeg3_audio_channels(input, astream);

			quicktime_set_audio(output, 
				channels, 
				mpeg3_sample_rate(input, 0), 
				24, 
				AUDIO_CODEC);

			audio_output = malloc(sizeof(float*) * channels);
			for(i = 0; i < channels; i++)
				audio_output[i] = malloc(sizeof(float) * afragment);
		}
	}
//printf("main 1\n");

//	quicktime_set_jpeg(output, 100, 0);
//	mpeg3_set_mmx(input, 0);

	while((!(do_video && mpeg3_end_of_video(input, layer)) || 
			!(do_audio && mpeg3_end_of_audio(input, astream))) &&
		(current_frame < frame_count || frame_count < 0))
	{
//printf("%d %d\n", mpeg3_end_of_video(input, layer), mpeg3_end_of_audio(input, astream));
		if(do_audio)
		{
			if(!mpeg3_end_of_audio(input, astream))
			{
				int fragment = afragment;
				int i, j, k;

				i = astream;
				k = 0;
				for(j = 0; j < mpeg3_audio_channels(input, i); j++, k++)
				{
					if(j == 0)
						mpeg3_read_audio(input, 
							audio_output[k], 	 /* Pointer to pre-allocated buffer of floats */
							0,      /* Pointer to pre-allocated buffer of int16's */
							j,          /* Channel to decode */
							fragment,         /* Number of samples to decode */
							i);
					else
						mpeg3_reread_audio(input, 
							audio_output[k], 	 /* Pointer to pre-allocated buffer of floats */
							0,      /* Pointer to pre-allocated buffer of int16's */
							j,          /* Channel to decode */
							fragment,         /* Number of samples to decode */
							i);
				}



				quicktime_encode_audio(output, 
					0, 
					audio_output, 
					fragment);

				current_sample += fragment;
				if(!do_video)
				{
					printf(" %d samples written\r", current_sample);
					fflush(stdout);
				}
			}
			else
				current_sample += afragment;
		}

		if(do_video)
		{
			if(!mpeg3_end_of_video(input, layer))
			{
				int fragment;
				if(do_audio)
					fragment = (long)((double)current_sample / 
							mpeg3_sample_rate(input, 0) *
							mpeg3_frame_rate(input, layer) - 
						current_frame);
				else
					fragment = 1;

				for(i = 0; i < fragment && !mpeg3_end_of_video(input, layer); i++)
				{
					mpeg3_read_yuvframe_ptr(input,
						&row_pointers[0],
						&row_pointers[1],
						&row_pointers[2],
						layer);

					switch(mpeg3_colormodel(input, layer))
					{
						case MPEG3_YUV420P:
							quicktime_set_cmodel(output, BC_YUV420P);
							break;
						case MPEG3_YUV422P:
							quicktime_set_cmodel(output, BC_YUV422P);
							break;
					}
					quicktime_encode_video(output, 
						(unsigned char **)row_pointers, 
						0);

					current_frame++;
					printf(" %d frames written\r", current_frame);
					fflush(stdout);
				}
			}
		}
	}
printf("main 2\n");

	printf("\n");
	quicktime_close(output);
	mpeg3_close(input);
}