【C/C++】使用DUMP8、DUMP16、DUMP32打印数据Buffer

1.前言

经常在编程时会遇到打印Data Buffer的情况,下面定义了DUMP8、DUMP16、DUMP32,很方便来打印Data Buffer里面的数据。

2.hal_print.c

#include "hal_print.h"

/**
 ****************************************************************************************
 * @brief       function used to Print data in a fixed format
 *
 * @param[in]   fmt      (Print format)
 *              size     (The size of the data)
 *              count    (Length of data)
 *              buffer   (The address where data is stored)
 *
 * @return      0(successful) or -1(fail)
 ****************************************************************************************
 */
int hal_print_dump(const char *fmt, unsigned int size,  unsigned int count, const void *buffer)
{
	char buf[255];
	unsigned int len=0,i=0;

	switch( size )
	{
		case sizeof(uint32_t):
			while(i<count && len<sizeof(buf))
			{
				len += HAL_SNPRINTF(&buf[len], sizeof(buf) - len, fmt, *(uint32_t *)((uint32_t *)buffer+i));
				i++;
			}
			break;
		case sizeof(uint16_t):
				while(i<count && len<sizeof(buf))
				{
					len += HAL_SNPRINTF(&buf[len], sizeof(buf) - len, fmt, *(uint16_t *)((uint16_t *)buffer+i));
					i++;
				}
				break;
		case sizeof(uint8_t):
		default:
			while(i<count && len<sizeof(buf))
			{
				len += HAL_SNPRINTF(&buf[len], sizeof(buf) - len, fmt, *(uint8_t *)((uint8_t *)buffer+i));
				i++;
			}
			break;
	}

    if (len + 1 < sizeof(buf)) {
        buf[len++] = '\r';
    }
    if (len + 1 < sizeof(buf)) {
        buf[len++] = '\n';
    }
    if (len + 1 < sizeof(buf)) {
        buf[len++] = '\0';
    }

    HAL_PRINT("%s",buf);

	return len;
}

3.hal_print.h

#ifndef __HAL_PRINT_H__
#define __HAL_PRINT_H__

/*******************************************************************************************
 * @brief Header files and macro definitions differ on each platform.
 *
 *******************************************************************************************/
#include "stdio.h"
#include "stdint.h"

#define	HAL_SNPRINTF		snprintf
#define HAL_PRINT			printf
/*******************************************************************************************/

int hal_print_dump(const char *fmt, unsigned int size,  unsigned int count, const void *buffer);


#define DUMP8(str, buf, cnt)        hal_print_dump(str, sizeof(uint8_t), cnt, buf)
#define DUMP16(str, buf, cnt)       hal_print_dump(str, sizeof(uint16_t), cnt, buf)
#define DUMP32(str, buf, cnt)       hal_print_dump(str, sizeof(uint32_t), cnt, buf)

#endif // __HAL_PRINT_H__

4.main.c

#include "stdio.h"
#include "stdint.h"
#include "hal_print.h"

uint8_t dataBuf[52];

int main(void)
{
	uint8_t i;
	
	// init data 
	for(i = 0; i < sizeof(dataBuf); i++)
	{
		dataBuf[i] = i + 1;
	}
	
	// print data
	printf("DUMP8:\r\n");
	DUMP8("0x%02x ", dataBuf, 30);
	
	printf("\r\nDUMP16:\r\n");
	DUMP16("0x%04x ", dataBuf, 20);
	
	printf("\r\nDUMP32:\r\n");
	DUMP32("0x%08x ", dataBuf, 10);
	
	return 0;
}

5.测试效果

在这里插入图片描述

6.资料下载

完整的代码下载地址如下:
https://download.csdn.net/download/ZHONGCAI0901/15482516

以下是使用FFmpeg库推流本地文件,并实现跳转和倍速播放的完整代码。 ```c++ #include <iostream> #include <string> extern "C" { #include <libavcodec/avcodec.h> #include <libavformat/avformat.h> #include <libavutil/opt.h> #include <libavutil/time.h> #include <libswresample/swresample.h> #include <libswscale/swscale.h> } using namespace std; int main(int argc, char *argv[]) { if (argc < 5) { cerr << "Usage: " << argv[0] << " input_file output_url seek_time speed\n"; return -1; } const char *input_file = argv[1]; const char *output_url = argv[2]; const double seek_time = atof(argv[3]); const double speed = atof(argv[4]); av_register_all(); AVFormatContext *fmt_ctx = nullptr; if (avformat_open_input(&fmt_ctx, input_file, nullptr, nullptr) != 0) { cerr << "Failed to open input file" << endl; return -1; } if (avformat_find_stream_info(fmt_ctx, nullptr) < 0) { cerr << "Failed to retrieve input stream information" << endl; return -1; } AVStream *stream = nullptr; int stream_index = av_find_best_stream(fmt_ctx, AVMEDIA_TYPE_VIDEO, -1, -1, &stream, 0); if (stream_index < 0) { cerr << "Failed to find video stream" << endl; return -1; } AVCodecParameters *codecpar = stream->codecpar; AVCodec *decoder = avcodec_find_decoder(codecpar->codec_id); if (decoder == nullptr) { cerr << "Failed to find decoder" << endl; return -1; } AVCodecContext *codec_ctx = avcodec_alloc_context3(decoder); if (avcodec_parameters_to_context(codec_ctx, codecpar) < 0) { cerr << "Failed to copy codec parameters to decoder context" << endl; return -1; } if (avcodec_open2(codec_ctx, decoder, nullptr) < 0) { cerr << "Failed to open codec" << endl; return -1; } AVFrame *frame = av_frame_alloc(); if (frame == nullptr) { cerr << "Failed to allocate frame" << endl; return -1; } AVPacket *pkt = av_packet_alloc(); if (pkt == nullptr) { cerr << "Failed to allocate packet" << endl; return -1; } AVDictionary *opts = nullptr; av_dict_set(&opts, "bufsize", "1024000", 0); av_dict_set(&opts, "maxrate", "1024000", 0); AVFormatContext *out_fmt_ctx = nullptr; if (avformat_alloc_output_context2(&out_fmt_ctx, nullptr, "flv", output_url) < 0) { cerr << "Failed to allocate output context" << endl; return -1; } AVStream *out_stream = avformat_new_stream(out_fmt_ctx, nullptr); if (out_stream == nullptr) { cerr << "Failed to create output stream" << endl; return -1; } if (avcodec_parameters_copy(out_stream->codecpar, codecpar) < 0) { cerr << "Failed to copy codec parameters to output stream" << endl; return -1; } if (avio_open(&out_fmt_ctx->pb, output_url, AVIO_FLAG_WRITE) < 0) { cerr << "Failed to open output url" << endl; return -1; } if (avformat_write_header(out_fmt_ctx, &opts) < 0) { cerr << "Failed to write output header" << endl; return -1; } av_dump_format(fmt_ctx, 0, input_file, 0); int64_t seek_target = seek_time * AV_TIME_BASE; if (av_seek_frame(fmt_ctx, stream_index, seek_target, AVSEEK_FLAG_BACKWARD) < 0) { cerr << "Failed to seek to " << seek_time << endl; return -1; } SwsContext *sws_ctx = sws_getContext(codec_ctx->width, codec_ctx->height, codec_ctx->pix_fmt, codec_ctx->width, codec_ctx->height, AV_PIX_FMT_YUV420P, 0, nullptr, nullptr, nullptr); if (sws_ctx == nullptr) { cerr << "Failed to allocate sws context" << endl; return -1; } AVRational frame_rate = stream->r_frame_rate; AVRational time_base = stream->time_base; AVRational out_time_base = out_stream->time_base; int64_t next_pts = 0; double speed_factor = 1.0 / speed; while (av_read_frame(fmt_ctx, pkt) >= 0) { if (pkt->stream_index != stream_index) { av_packet_unref(pkt); continue; } if (avcodec_send_packet(codec_ctx, pkt) < 0) { cerr << "Failed to send packet to decoder" << endl; return -1; } while (avcodec_receive_frame(codec_ctx, frame) == 0) { double pts = static_cast<double>(frame->pts) * time_base.num / time_base.den; double dts = static_cast<double>(frame->pkt_dts) * time_base.num / time_base.den; double duration = static_cast<double>(frame->pkt_duration) * time_base.num / time_base.den; if (pts < seek_time) { av_frame_unref(frame); continue; } if (duration > 0) { duration *= speed_factor; frame->pkt_duration = static_cast<int64_t>(duration * time_base.den / time_base.num); } if (pts >= next_pts) { int64_t pts_ms = static_cast<int64_t>(pts * 1000); int64_t out_pts = av_rescale_q(pts_ms, {1, 1000}, out_time_base); int64_t delay_ms = static_cast<int64_t>((pts - next_pts) * 1000 * speed_factor); int64_t delay = av_rescale_q(delay_ms, {1, 1000}, out_time_base); av_usleep(delay); AVFrame *out_frame = av_frame_alloc(); if (out_frame == nullptr) { cerr << "Failed to allocate output frame" << endl; return -1; } out_frame->format = AV_PIX_FMT_YUV420P; out_frame->width = codec_ctx->width; out_frame->height = codec_ctx->height; av_frame_get_buffer(out_frame, 0); sws_scale(sws_ctx, frame->data, frame->linesize, 0, codec_ctx->height, out_frame->data, out_frame->linesize); out_frame->pts = out_pts; if (avcodec_send_frame(out_stream->codec, out_frame) < 0) { cerr << "Failed to send frame to encoder" << endl; return -1; } while (avcodec_receive_packet(out_stream->codec, pkt) == 0) { pkt->stream_index = out_stream->index; av_interleaved_write_frame(out_fmt_ctx, pkt); av_packet_unref(pkt); } av_frame_unref(out_frame); next_pts += static_cast<int64_t>(duration * AV_TIME_BASE); } av_frame_unref(frame); } av_packet_unref(pkt); } av_write_trailer(out_fmt_ctx); av_packet_free(&pkt); av_frame_free(&frame); avcodec_free_context(&codec_ctx); avformat_close_input(&fmt_ctx); avio_closep(&out_fmt_ctx->pb); avformat_free_context(out_fmt_ctx); sws_freeContext(sws_ctx); return 0; } ``` 使用方法: ```bash ./push_stream input_file output_url seek_time speed ``` 其中,`input_file` 是输入的本地文件名,`output_url` 是输出的推流地址,`seek_time` 是跳转的时间(单位秒),`speed` 是倍速播放的速度。例如: ```bash ./push_stream input.mp4 rtmp://127.0.0.1/live/test 30 2.0 ``` 表示将 `input.mp4` 推流到 `rtmp://127.0.0.1/live/test`,从第 30 秒开始播放,以两倍速度播放。
评论 5
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值