UltraGrid
UltraGrid Low-Latency High-Resolution Transmission System
Loading...
Searching...
No Matches
ldgm-session-gpu.cpp
Go to the documentation of this file.
1/*
2 * =====================================================================================
3 *
4 * Filename: ldgm-session-gpu.cpp
5 *
6 * Description:
7 *
8 * Version: 1.0
9 * Created: 04/20/2012 02:21:11 PM
10 * Revision: none
11 * Compiler: gcc
12 *
13 * Authors: Milan Kabat (kabat@ics.muni.cz), Vojtech David (374572@mail.muni.cz)
14 * Organization: FI MUNI
15 *
16 * =====================================================================================
17 */
18#include <assert.h>
19#include <stdlib.h>
20#include <stdio.h>
21#include <time.h>
22#include <set>
23#include <ctype.h>
24#include <string.h>
25#include <iostream>
26#include <fstream>
27#include <map>
28#include <cuda_runtime.h>
29
30#include "ldgm-session-gpu.h"
31#include "ldgm-session-cpu.h"
32#include "gpu.cuh"
33#include "timer-util.h"
34#include "tanner.h"
35
36// static int * error_vec;
37// static int * sync_vec;
38
39// static int * ERROR_VEC;
40// static int * SYNC_VEC;
41
42
43// static int * PCM;
44
46 printf("GPU LDGM in progress .... \n");
47
48 error_vec=NULL;
49 sync_vec=NULL;
50
51 ERROR_VEC=NULL;
52 SYNC_VEC=NULL;
53
54 PCM=NULL;
55
57 OUTBUF=NULL;
58}
59
61 printf("LDGM TIME GPU: %f ms\n",this->elapsed_sum2/(double)this->no_frames2 );
62 cudaError_t error;
63 while (!freeBuffers.empty()) {
64 char *buf = freeBuffers.front();
65 freeBuffers.pop();
66 error = cudaFreeHost(buf);
67 if(error != cudaSuccess)printf("memoryPool: %s\n", cudaGetErrorString(error));
68 }
69
70 error = cudaFreeHost(error_vec);
71 cuda_check_error("error_vec");
72 error = cudaFreeHost(sync_vec);
73 cuda_check_error("sync_vec");
74
75
76 // cudaFree(OUTBUF);
78
81} /* destructor */
82
83void *LDGM_session_gpu::alloc_buf (int buf_size)
84{
85 // printf("cudaHostAlloc %d %d\n",this->indexMemoryPool,index);
86 // printf("buf_size %d, bufferSize %d\n",buf_size,this->memoryPoolSize[index] );
87 while (!freeBuffers.empty()) {
88 char *buf = freeBuffers.front();
89 freeBuffers.pop();
90
91 if (buf_size <= (int) bufferSizes[buf]) {
92 return buf;
93 } else {
94 cudaFreeHost(buf);
95 cuda_check_error("cudaFreeHost");
96 bufferSizes.erase(buf);
97 }
98 }
99
100 char *buf;
101 cudaHostAlloc((void **) &buf, buf_size, cudaHostAllocDefault);
102 // cudaHostAlloc(&this->memoryPool[index], buf_size, cudaHostAllocMapped);
103 cuda_check_error("cudaHostAlloc");
104 bufferSizes[buf] = buf_size;
105
106 return buf;
107}
108
110{
111 if ( buf != NULL ) {
112 freeBuffers.push(buf);
113 }
114}
115
116void LDGM_session_gpu::encode ( char *source_data, char *parity )
117{
118 assert(parity == source_data+param_k*get_packet_size());
119
120 unsigned int w_f = max_row_weight + 2;
121 unsigned int buf_size = (param_k + param_m) * packet_size;
122
123 cudaError_t error;
124
125 // error = cudaHostGetDevicePointer( &(out_buf_d), source_data, 0);
126 // cuda_check_error("out_buf_d");
127
128 if(OUTBUF==NULL){
129 // puts("cudaMalloc");
130 cudaMalloc((void **) &OUTBUF,buf_size);
131 OUTBUF_SIZE=buf_size;
132 }
133 if((int)buf_size>OUTBUF_SIZE){
134 // puts("cudaMalloc");
136 cudaMalloc((void **) &OUTBUF,buf_size);
137 OUTBUF_SIZE=buf_size;
138 }
139
140 cudaMemcpy((void *) OUTBUF,source_data,buf_size,cudaMemcpyHostToDevice);
141 cuda_check_error("memcpy OUTBUF");
142
143
144
145 if (PCM == NULL)
146 {
147 // puts("cudaMalloc");
148 error = cudaMalloc((void **) &PCM, w_f * param_m * sizeof(int));
149 if(error != cudaSuccess)printf("7CUDA error: %s\n", cudaGetErrorString(error));
150
151 error = cudaMemcpy(PCM, pcm, w_f * param_m * sizeof(int), cudaMemcpyHostToDevice);
152 if(error != cudaSuccess)printf("8CUDA error: %s\n", cudaGetErrorString(error));
153 }
154
155
156
157
158
159 gpu_encode_upgrade(source_data,OUTBUF , PCM, param_k, param_m, w_f, packet_size, buf_size);
160
161 // puts("end");
162
163}
164
165char *LDGM_session_gpu::decode_frame ( char *received_data, int buf_size, int *frame_size, std::map<int, int> valid_data )
166{
167 char *received = received_data;
168
169 Timer_util interval;
170 interval.start();
171
172 int p_size = buf_size / (param_m + param_k);
173 // printf("%d p_size K: %d, M: %d, buf_size: %d, max_row_weight: %d \n",p_size,param_k,param_m,buf_size,max_row_weight);
174
175 //We need to merge intervals in the valid data vector
176 std::map <int, int> merged_intervals;
177 std::map<int, int>::iterator map_it;
178
179 if ( valid_data.size() != 0 )
180 {
181 for ( map_it = valid_data.begin(); map_it != valid_data.end(); )
182 {
183 int start = map_it->first;
184 int length = map_it->second;
185 while ( start + length == (++map_it)->first )
186 length += map_it->second;
187 merged_intervals.insert ( std::pair<int, int> (start, length) );
188 }
189 }
190
191
192
193 cudaError_t error;
194 if (error_vec == NULL)
195 {
196 cudaHostAlloc((void **) &error_vec, sizeof(int) * (param_k + param_m), cudaHostAllocDefault );
197 cuda_check_error("error_vec");
198 }
199
200 if (sync_vec == NULL)
201 {
202 cudaHostAlloc((void **) &sync_vec, sizeof(int) * (param_k + param_m), cudaHostAllocDefault );
203 cuda_check_error("sync_vec");
204 }
205
206 // error_vec= (int* ) malloc(sizeof(int)*(param_k+param_m));
207 memset(error_vec, 0, sizeof(int) * (param_k + param_m));
208 // sync_vec= (int* ) malloc(sizeof(int)*(param_k+param_m));
209 memset(sync_vec, 0, sizeof(int) * (param_k + param_m));
210 int not_done = 0;
211
212 if ( merged_intervals.size() != 0
213 )
214 {
215
216 for (int i = 0; i < param_k + param_m; i++)
217 {
218 int node_offset = i * p_size;
219
220 map_it = merged_intervals.begin();
221
222 bool found = false;
223 while ( (map_it->first <= node_offset) && map_it != merged_intervals.end() )
224 {
225 map_it++;
226 found = true;
227 }
228 if ( found ) map_it--;
229
230 if ( found && (map_it->first + map_it->second) >=
231 (node_offset + p_size) )
232 {
233 //OK
234 error_vec[i] = 0;
235 sync_vec[i] = 0;
236 }
237 else
238 {
239 //NOK
240 memset(received + (i * p_size), 0x0, p_size);
241 error_vec[i] = 1;
242 sync_vec[i] = 1;
243 not_done++;
244 }
245
246 }
247
248 }
249
250
251
252 //-------------------------------------------------------------------------------------------------------
253
254
255
256
257
258 /*
259 * struct coding_params params;
260 * params.k = param_k;
261 * params.m = param_m;
262 * params.max_row_weight = max_row_weight;
263 * params.packet_size = p_size;
264 * params.buf_size = buf_size;
265 */
266 unsigned int w_f = max_row_weight + 2;
267
268
269 // printf("K: %d, M: %d, max_row_weight: %d, buf_size: %d,\n", param_k, param_m, max_row_weight, buf_size );
270 // printf("not done: %d\n", not_done);
271
272 // int * sync_vec_d;
273 // int * error_vec_d;
274 // int * pcm_d;
275
276 if (PCM == NULL)
277 {
278 error = cudaMalloc((void **) &PCM, w_f * param_m * sizeof(int));
279 if (error != cudaSuccess) printf("3 %s\n", cudaGetErrorString(error));
280
281 error = cudaMemcpy(PCM, pcm, w_f * param_m * sizeof(int), cudaMemcpyHostToDevice);
282 if (error != cudaSuccess) printf("4 %s\n", cudaGetErrorString(error));
283 }
284
285 if (SYNC_VEC == NULL)
286 {
287 error = cudaMalloc((void **) &SYNC_VEC, (param_m + param_k) * sizeof(int));
288 if (error != cudaSuccess) printf("7 %s\n", cudaGetErrorString(error));
289 }
290
292 cuda_check_error("SYNC_VEC");
293
294
295 if (ERROR_VEC == NULL)
296 {
297 cudaMalloc((void **) &ERROR_VEC, (param_m + param_k) * sizeof(int));
298 cuda_check_error("ERROR_VEC");
299 }
300
302 cuda_check_error("ERROR_VEC");
303
304 // // }else{
305 // // error = cudaMemcpy(ERROR_VEC, sync_vec, (param_m + param_k) * sizeof(int), cudaMemcpyHostToDevice);
306 // // if (error != cudaSuccess) printf("8 %s\n", cudaGetErrorString(error));
307 // // }
308
309 //(char *data, int * PCM,int* SYNC_VEC,int* ERROR_VEC, int not_done, int *frame_size,int * error_vec,int * sync_vec,int M,int K,int w_f,int buf_size,int packet_size)
310 // if (not_done != 0)
311 // {
312 // gpu_decode_upgrade(received, PCM, SYNC_VEC, ERROR_VEC, not_done, frame_size, error_vec, sync_vec, param_m, param_k, w_f, buf_size, p_size);
313 // }
314 // else
315 // {
316 // int fs = 0;
317 // memcpy(&fs, received, 4);
318 // *frame_size = fs;
319 // printf("frame_size: %d\n",frame_size );
320 // }
321
322 gpu_decode_upgrade(received, PCM, SYNC_VEC, ERROR_VEC, not_done, frame_size, error_vec, sync_vec, param_m, param_k, w_f, buf_size, p_size);
323
324#if 0
325 assert(LDGM_session::HEADER_SIZE >= 12)
326 int my_frame_size = 0;
327 memcpy(&my_frame_size, received + 8, 4);
328 int crc_origin = 0;
329 memcpy(&crc_origin, received + 4, 4);
330
331 // printf("my_frame_size: %d\n",my_frame_size );
332 int crc =0;
333 crc = crc32buf(received + LDGM_session::HEADER_SIZE, my_frame_size);
334
335 if (crc_origin != crc)
336 {
337 printf("CRC NOK\n");
338
339 }
340#endif
341
342 // if (*frame_size != 0)
343 // {
344
345 // int my_frame_size = 0;
346 // memcpy(&my_frame_size, received + 8, 4);
347 // int crc_origin = 0;
348 // memcpy(&crc_origin, received + 4, 4);
349
350 // // printf("my_frame_size: %d\n",my_frame_size );
351 // int crc =0;
352 // // crc32buf(received + 12, my_frame_size);
353
354 // if (crc_origin != crc)
355 // {
356 // printf("CRC NOK1\n");
357
358 // }
359 // }
360 // else
361 // {
362 // printf("CRC NOK\n");
363 // }
364
365 interval.end();
366 //printf("time: %e\n",elapsed/1000.0 );
367 this->elapsed_sum2 += interval.elapsed_time_ms();
368 this->no_frames2++;
369
370 return received + LDGM_session::HEADER_SIZE;
371
372}
373
374
std::map< char *, size_t > bufferSizes
char * decode_frame(char *received_data, int buf_size, int *frame_size, std::map< int, int > valid_data)
void encode(char *data_ptr, char *parity_ptr)
void free_out_buf(char *buf)
std::queue< char * > freeBuffers
void * alloc_buf(int size)
static const int HEADER_SIZE
unsigned short param_m
double elapsed_sum2
unsigned short max_row_weight
unsigned short param_k
unsigned short packet_size
unsigned int get_packet_size() const
This class implements timer utils.
Definition timer-util.h:26
void end()
Definition timer-util.h:36
double elapsed_time_ms() const
Definition timer-util.h:52
void start()
Definition timer-util.h:32
uint32_t crc32buf(const char *buf, size_t len)
Definition crc_32.c:176
#define cudaMemcpy
#define cudaSuccess
#define cudaFree
#define cudaHostAllocDefault
#define cudaMemcpyHostToDevice
#define cudaHostAlloc
#define cudaMalloc
#define cudaFreeHost
#define cudaError_t
#define cudaGetErrorString
void gpu_encode_upgrade(char *source_data, int *OUTBUF, int *PCM, int param_k, int param_m, int w_f, int packet_size, int buf_size)
Definition gpu.cu:113
void gpu_decode_upgrade(char *data, int *PCM, int *SYNC_VEC, int *ERROR_VEC, int not_done, int *frame_size, int *error_vec, int *sync_vec, int M, int K, int w_f, int buf_size, int packet_size)
Definition gpu.cu:194
codec_t first
Definition sdl2.c:423
static void start()
Definition sdp.c:202