Main Page | Alphabetical List | Data Structures | File List | Data Fields | Globals

translate.h File Reference

#include <asterisk/frame.h>

Include dependency graph for translate.h:

Include dependency graph

This graph shows which files directly or indirectly include this file:

Included by dependency graph

Go to the source code of this file.

Data Structures

struct  ast_translator
 data structure associated with a translator More...


Defines

#define MAX_FORMAT   32

Functions

int ast_register_translator (struct ast_translator *t)
 Register a translator.

int ast_unregister_translator (struct ast_translator *t)
 Unregister a translator.

int ast_translator_best_choice (int *dsts, int *srcs)
 Chooses the best translation path.

ast_trans_pvtast_translator_build_path (int dest, int source)
 Builds a translator path.

void ast_translator_free_path (struct ast_trans_pvt *tr)
 Frees a translator path.

ast_frameast_translate (struct ast_trans_pvt *tr, struct ast_frame *f, int consume)
 translates one or more frames


Define Documentation

#define MAX_FORMAT   32
 

Definition at line 17 of file translate.h.

Referenced by ast_register_translator(), and ast_translator_best_choice().


Function Documentation

int ast_register_translator struct ast_translator t  ) 
 

Register a translator.

Parameters:
t populated ast_translator structure This registers a codec translator with asterisk Returns 0 on success, -1 on failure

Definition at line 389 of file translate.c.

References ast_cli_register(), ast_getformatname(), ast_log(), ast_mutex_lock, ast_mutex_unlock, ast_verbose(), COLOR_BLACK, COLOR_MAGENTA, ast_translator::cost, ast_translator::dstfmt, LOG_WARNING, MAX_FORMAT, ast_translator::name, ast_translator::next, option_verbose, ast_translator::srcfmt, term_color(), and VERBOSE_PREFIX_2.

00390 { 00391 char tmp[80]; 00392 t->srcfmt = powerof(t->srcfmt); 00393 t->dstfmt = powerof(t->dstfmt); 00394 if ((t->srcfmt >= MAX_FORMAT) || (t->dstfmt >= MAX_FORMAT)) { 00395 ast_log(LOG_WARNING, "Format %s is larger than MAX_FORMAT\n", ast_getformatname(t->srcfmt)); 00396 return -1; 00397 } 00398 calc_cost(t,1); 00399 if (option_verbose > 1) 00400 ast_verbose(VERBOSE_PREFIX_2 "Registered translator '%s' from format %s to %s, cost %d\n", term_color(tmp, t->name, COLOR_MAGENTA, COLOR_BLACK, sizeof(tmp)), ast_getformatname(1 << t->srcfmt), ast_getformatname(1 << t->dstfmt), t->cost); 00401 ast_mutex_lock(&list_lock); 00402 if (!added_cli) { 00403 ast_cli_register(&show_trans); 00404 added_cli++; 00405 } 00406 t->next = list; 00407 list = t; 00408 rebuild_matrix(0); 00409 ast_mutex_unlock(&list_lock); 00410 return 0; 00411 }

struct ast_frame* ast_translate struct ast_trans_pvt tr,
struct ast_frame f,
int  consume
 

translates one or more frames

Parameters:
tr translator structure to use for translation
f frame to translate
consume Whether or not to free the original frame Apply an input frame into the translator and receive zero or one output frames. Consume determines whether the original frame should be freed Returns an ast_frame of the new translation format on success, NULL on failure

Definition at line 138 of file translate.c.

References ast_frfree(), ast_log(), ast_frame::delivery, ast_translator::framein, LOG_WARNING, ast_frame::samples, and ast_trans_pvt::step.

Referenced by ast_read(), ast_write(), and ast_writestream().

00139 { 00140 struct ast_trans_pvt *p; 00141 struct ast_frame *out; 00142 struct timeval delivery; 00143 p = path; 00144 /* Feed the first frame into the first translator */ 00145 p->step->framein(p->state, f); 00146 if (f->delivery.tv_sec || f->delivery.tv_usec) { 00147 if (path->nextin.tv_sec || path->nextin.tv_usec) { 00148 /* Make sure this is in line with what we were expecting */ 00149 if ((path->nextin.tv_sec != f->delivery.tv_sec) || 00150 (path->nextin.tv_usec != f->delivery.tv_usec)) { 00151 /* The time has changed between what we expected and this 00152 most recent time on the new packet. Adjust our output 00153 time appropriately */ 00154 long sdiff; 00155 long udiff; 00156 sdiff = f->delivery.tv_sec - path->nextin.tv_sec; 00157 udiff = f->delivery.tv_usec - path->nextin.tv_usec; 00158 path->nextin.tv_sec = f->delivery.tv_sec; 00159 path->nextin.tv_usec = f->delivery.tv_usec; 00160 path->nextout.tv_sec += sdiff; 00161 path->nextout.tv_usec += udiff; 00162 if (path->nextout.tv_usec < 0) { 00163 path->nextout.tv_usec += 1000000; 00164 path->nextout.tv_sec--; 00165 } else if (path->nextout.tv_usec >= 1000000) { 00166 path->nextout.tv_usec -= 1000000; 00167 path->nextout.tv_sec++; 00168 } 00169 } 00170 } else { 00171 /* This is our first pass. Make sure the timing looks good */ 00172 path->nextin.tv_sec = f->delivery.tv_sec; 00173 path->nextin.tv_usec = f->delivery.tv_usec; 00174 path->nextout.tv_sec = f->delivery.tv_sec; 00175 path->nextout.tv_usec = f->delivery.tv_usec; 00176 } 00177 /* Predict next incoming sample */ 00178 path->nextin.tv_sec += (f->samples / 8000); 00179 path->nextin.tv_usec += ((f->samples % 8000) * 125); 00180 if (path->nextin.tv_usec >= 1000000) { 00181 path->nextin.tv_usec -= 1000000; 00182 path->nextin.tv_sec++; 00183 } 00184 } 00185 delivery.tv_sec = f->delivery.tv_sec; 00186 delivery.tv_usec = f->delivery.tv_usec; 00187 if (consume) 00188 ast_frfree(f); 00189 while(p) { 00190 out = p->step->frameout(p->state); 00191 /* If we get nothing out, return NULL */ 00192 if (!out) 00193 return NULL; 00194 /* If there is a next state, feed it in there. If not, 00195 return this frame */ 00196 if (p->next) 00197 p->next->step->framein(p->next->state, out); 00198 else { 00199 if (delivery.tv_sec || delivery.tv_usec) { 00200 /* Use next predicted outgoing timestamp */ 00201 out->delivery.tv_sec = path->nextout.tv_sec; 00202 out->delivery.tv_usec = path->nextout.tv_usec; 00203 00204 /* Predict next outgoing timestamp from samples in this 00205 frame. */ 00206 path->nextout.tv_sec += (out->samples / 8000); 00207 path->nextout.tv_usec += ((out->samples % 8000) * 125); 00208 if (path->nextout.tv_usec >= 1000000) { 00209 path->nextout.tv_sec++; 00210 path->nextout.tv_usec -= 1000000; 00211 } 00212 } else { 00213 out->delivery.tv_sec = 0; 00214 out->delivery.tv_usec = 0; 00215 } 00216 return out; 00217 } 00218 p = p->next; 00219 } 00220 ast_log(LOG_WARNING, "I should never get here...\n"); 00221 return NULL; 00222 }

int ast_translator_best_choice int *  dsts,
int *  srcs
 

Chooses the best translation path.

Given a list of sources, and a designed destination format, which should I choose? Returns 0 on success, -1 if no path could be found. Modifies dests and srcs in place

Definition at line 437 of file translate.c.

References ast_mutex_lock, ast_mutex_unlock, ast_translator_dir::cost, MAX_FORMAT, and ast_translator_dir::step.

Referenced by ast_channel_make_compatible(), ast_request(), ast_set_read_format(), and ast_set_write_format().

00438 { 00439 /* Calculate our best source format, given costs, and a desired destination */ 00440 int x,y; 00441 int best=-1; 00442 int bestdst=0; 00443 int cur = 1; 00444 int besttime=999999999; 00445 ast_mutex_lock(&list_lock); 00446 for (y=0;y<MAX_FORMAT;y++) { 00447 if ((cur & *dst) && (cur & *srcs)) { 00448 /* This is a common format to both. Pick it if we don't have one already */ 00449 besttime=0; 00450 bestdst = cur; 00451 best = cur; 00452 break; 00453 } 00454 if (cur & *dst) 00455 for (x=0;x<MAX_FORMAT;x++) { 00456 if (tr_matrix[x][y].step && /* There's a step */ 00457 (tr_matrix[x][y].cost < besttime) && /* We're better than what exists now */ 00458 (*srcs & (1 << x))) /* x is a valid source format */ 00459 { 00460 best = 1 << x; 00461 bestdst = cur; 00462 besttime = tr_matrix[x][y].cost; 00463 } 00464 } 00465 cur = cur << 1; 00466 } 00467 if (best > -1) { 00468 *srcs = best; 00469 *dst = bestdst; 00470 best = 0; 00471 } 00472 ast_mutex_unlock(&list_lock); 00473 return best; 00474 }

struct ast_trans_pvt* ast_translator_build_path int  dest,
int  source
 

Builds a translator path.

Parameters:
dest destination format
source source format Build a path (possibly NULL) from source to dest Returns ast_trans_pvt on success, NULL on failure

Definition at line 88 of file translate.c.

References ast_getformatname(), ast_log(), free, LOG_WARNING, malloc, ast_translator::new, and ast_translator_dir::step.

Referenced by ast_set_read_format(), ast_set_write_format(), and ast_writestream().

00089 { 00090 struct ast_trans_pvt *tmpr = NULL, *tmp = NULL; 00091 /* One of the hardest parts: Build a set of translators based upon 00092 the given source and destination formats */ 00093 source = powerof(source); 00094 dest = powerof(dest); 00095 while(source != dest) { 00096 if (tr_matrix[source][dest].step) { 00097 if (tmp) { 00098 tmp->next = malloc(sizeof(struct ast_trans_pvt)); 00099 tmp = tmp->next; 00100 } else 00101 tmp = malloc(sizeof(struct ast_trans_pvt)); 00102 00103 00104 if (tmp) { 00105 tmp->next = NULL; 00106 tmp->nextin.tv_sec = 0; 00107 tmp->nextin.tv_usec = 0; 00108 tmp->nextout.tv_sec = 0; 00109 tmp->nextout.tv_usec = 0; 00110 tmp->step = tr_matrix[source][dest].step; 00111 tmp->state = tmp->step->new(); 00112 if (!tmp->state) { 00113 ast_log(LOG_WARNING, "Failed to build translator step from %d to %d\n", source, dest); 00114 free(tmp); 00115 tmp = NULL; 00116 return NULL; 00117 } 00118 /* Set the root, if it doesn't exist yet... */ 00119 if (!tmpr) 00120 tmpr = tmp; 00121 /* Keep going if this isn't the final destination */ 00122 source = tmp->step->dstfmt; 00123 } else { 00124 /* XXX This could leak XXX */ 00125 ast_log(LOG_WARNING, "Out of memory\n"); 00126 return NULL; 00127 } 00128 } else { 00129 /* We shouldn't have allocated any memory */ 00130 ast_log(LOG_WARNING, "No translator path from %s to %s\n", 00131 ast_getformatname(source), ast_getformatname(dest)); 00132 return NULL; 00133 } 00134 } 00135 return tmpr; 00136 }

void ast_translator_free_path struct ast_trans_pvt tr  ) 
 

Frees a translator path.

Parameters:
tr translator path to get rid of Frees the given translator path structure

Definition at line 75 of file translate.c.

References ast_translator::destroy, free, ast_trans_pvt::next, and ast_trans_pvt::step.

Referenced by ast_channel_free(), ast_closestream(), ast_set_read_format(), ast_set_write_format(), and ast_writestream().

00076 { 00077 struct ast_trans_pvt *pl, *pn; 00078 pn = p; 00079 while(pn) { 00080 pl = pn; 00081 pn = pn->next; 00082 if (pl->state && pl->step->destroy) 00083 pl->step->destroy(pl->state); 00084 free(pl); 00085 } 00086 }

int ast_unregister_translator struct ast_translator t  ) 
 

Unregister a translator.

Parameters:
t translator to unregister Unregisters the given tranlator Returns 0 on success, -1 on failure

Definition at line 413 of file translate.c.

References ast_getformatname(), ast_mutex_lock, ast_mutex_unlock, ast_verbose(), COLOR_BLACK, COLOR_MAGENTA, ast_translator::dstfmt, ast_translator::name, ast_translator::next, option_verbose, ast_translator::srcfmt, term_color(), and VERBOSE_PREFIX_2.

00414 { 00415 char tmp[80]; 00416 struct ast_translator *u, *ul = NULL; 00417 ast_mutex_lock(&list_lock); 00418 u = list; 00419 while(u) { 00420 if (u == t) { 00421 if (ul) 00422 ul->next = u->next; 00423 else 00424 list = u->next; 00425 if (option_verbose > 1) 00426 ast_verbose(VERBOSE_PREFIX_2 "Unregistered translator '%s' from format %s to %s\n", term_color(tmp, t->name, COLOR_MAGENTA, COLOR_BLACK, sizeof(tmp)), ast_getformatname(1 << t->srcfmt), ast_getformatname(1 << t->dstfmt)); 00427 break; 00428 } 00429 ul = u; 00430 u = u->next; 00431 } 00432 rebuild_matrix(0); 00433 ast_mutex_unlock(&list_lock); 00434 return (u ? 0 : -1); 00435 }


Generated on Sat Jun 12 16:41:49 2004 for Asterisk by doxygen 1.3.7