Mercurial > hg > audiostuff
comparison spandsp-0.0.3/spandsp-0.0.3/src/spandsp/t38_core.h @ 5:f762bf195c4b
import spandsp-0.0.3
author | Peter Meerwald <pmeerw@cosy.sbg.ac.at> |
---|---|
date | Fri, 25 Jun 2010 16:00:21 +0200 |
parents | |
children |
comparison
equal
deleted
inserted
replaced
4:26cd8f1ef0b1 | 5:f762bf195c4b |
---|---|
1 /* | |
2 * SpanDSP - a series of DSP components for telephony | |
3 * | |
4 * t38_core.h - An implementation of T.38, less the packet exchange part | |
5 * | |
6 * Written by Steve Underwood <steveu@coppice.org> | |
7 * | |
8 * Copyright (C) 2005 Steve Underwood | |
9 * | |
10 * All rights reserved. | |
11 * | |
12 * This program is free software; you can redistribute it and/or modify | |
13 * it under the terms of the GNU General Public License version 2, as | |
14 * published by the Free Software Foundation. | |
15 * | |
16 * This program is distributed in the hope that it will be useful, | |
17 * but WITHOUT ANY WARRANTY; without even the implied warranty of | |
18 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | |
19 * GNU General Public License for more details. | |
20 * | |
21 * You should have received a copy of the GNU General Public License | |
22 * along with this program; if not, write to the Free Software | |
23 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. | |
24 * | |
25 * $Id: t38_core.h,v 1.11 2006/12/07 13:22:26 steveu Exp $ | |
26 */ | |
27 | |
28 /*! \file */ | |
29 | |
30 #if !defined(_T38_CORE_H_) | |
31 #define _T38_CORE_H_ | |
32 | |
33 /*! \page t38_core_page T.38 real time FAX over IP message handling | |
34 There are two ITU recommendations which address sending FAXes over IP networks. T.37 specifies a | |
35 method of encapsulating FAX images in e-mails, and transporting them to the recipient (an e-mail | |
36 box, or another FAX machine) in a store-and-forward manner. T.38 defines a protocol for | |
37 transmitting a FAX across an IP network in real time. The core T.38 modules implements the basic | |
38 message handling for the T.38, real time, FAX over IP (FoIP) protocol. | |
39 | |
40 The T.38 protocol can operate between: | |
41 - Internet-aware FAX terminals, which connect directly to an IP network. The T.38 terminal module | |
42 extends this module to provide a complete T.38 terminal. | |
43 - FAX gateways, which allow traditional PSTN FAX terminals to communicate through the Internet. | |
44 The T.38 gateway module extends this module to provide a T.38 gateway. | |
45 - A combination of terminals and gateways. | |
46 | |
47 T.38 is the only standardised protocol which exists for real-time FoIP. Reliably transporting a | |
48 FAX between PSTN FAX terminals, through an IP network, requires use of the T.38 protocol at FAX | |
49 gateways. VoIP connections are not robust for modem use, including FAX modem use. Most use low | |
50 bit rate codecs, which cannot convey the modem signals accurately. Even when high bit rate | |
51 codecs are used, VoIP connections suffer dropouts and timing adjustments, which modems cannot | |
52 tolerate. In a LAN environment the dropout rate may be very low, but the timing adjustments which | |
53 occur in VoIP connections still make modem operation unreliable. T.38 FAX gateways deal with the | |
54 delays, timing jitter, and packet loss experienced in packet networks, and isolate the PSTN FAX | |
55 terminals from these as far as possible. In addition, by sending FAXes as image data, rather than | |
56 digitised audio, they reduce the required bandwidth of the IP network. | |
57 | |
58 \section t38_core_page_sec_1 What does it do? | |
59 | |
60 \section t38_core_page_sec_2 How does it work? | |
61 | |
62 Timing differences and jitter between two T.38 entities can be a serious problem, if one of those | |
63 entities is a PSTN gateway. | |
64 | |
65 Flow control for non-ECM image data takes advantage of several features of the T.30 specification. | |
66 First, an unspecified number of 0xFF octets may be sent at the start of transmission. This means we | |
67 can add endless extra 0xFF bytes at this point, without breaking the T.30 spec. In practice, we | |
68 cannot add too many, or we will affect the timing tolerance of the T.30 protocol by delaying the | |
69 response at the end of each image. Secondly, just before an end of line (EOL) marker we can pad | |
70 with zero bits. Again, the number is limited only by need to avoid upsetting the timing of the | |
71 step following the non-ECM data. | |
72 */ | |
73 | |
74 enum t30_indicator_types_e | |
75 { | |
76 T38_IND_NO_SIGNAL = 0, | |
77 T38_IND_CNG, | |
78 T38_IND_CED, | |
79 T38_IND_V21_PREAMBLE, | |
80 T38_IND_V27TER_2400_TRAINING, | |
81 T38_IND_V27TER_4800_TRAINING, | |
82 T38_IND_V29_7200_TRAINING, | |
83 T38_IND_V29_9600_TRAINING, | |
84 T38_IND_V17_7200_SHORT_TRAINING, | |
85 T38_IND_V17_7200_LONG_TRAINING, | |
86 T38_IND_V17_9600_SHORT_TRAINING, | |
87 T38_IND_V17_9600_LONG_TRAINING, | |
88 T38_IND_V17_12000_SHORT_TRAINING, | |
89 T38_IND_V17_12000_LONG_TRAINING, | |
90 T38_IND_V17_14400_SHORT_TRAINING, | |
91 T38_IND_V17_14400_LONG_TRAINING, | |
92 T38_IND_V8_ANSAM, | |
93 T38_IND_V8_SIGNAL, | |
94 T38_IND_V34_CNTL_CHANNEL_1200, | |
95 T38_IND_V34_PRI_CHANNEL, | |
96 T38_IND_V34_CC_RETRAIN, | |
97 T38_IND_V33_12000_TRAINING, | |
98 T38_IND_V33_14400_TRAINING | |
99 }; | |
100 | |
101 enum t38_data_types_e | |
102 { | |
103 T38_DATA_NONE = -1, | |
104 T38_DATA_V21 = 0, | |
105 T38_DATA_V27TER_2400, | |
106 T38_DATA_V27TER_4800, | |
107 T38_DATA_V29_7200, | |
108 T38_DATA_V29_9600, | |
109 T38_DATA_V17_7200, | |
110 T38_DATA_V17_9600, | |
111 T38_DATA_V17_12000, | |
112 T38_DATA_V17_14400, | |
113 T38_DATA_V8, | |
114 T38_DATA_V34_PRI_RATE, | |
115 T38_DATA_V34_CC_1200, | |
116 T38_DATA_V34_PRI_CH, | |
117 T38_DATA_V33_12000, | |
118 T38_DATA_V33_14400 | |
119 }; | |
120 | |
121 enum t38_field_types_e | |
122 { | |
123 T38_FIELD_HDLC_DATA = 0, | |
124 T38_FIELD_HDLC_SIG_END, | |
125 T38_FIELD_HDLC_FCS_OK, | |
126 T38_FIELD_HDLC_FCS_BAD, | |
127 T38_FIELD_HDLC_FCS_OK_SIG_END, | |
128 T38_FIELD_HDLC_FCS_BAD_SIG_END, | |
129 T38_FIELD_T4_NON_ECM_DATA, | |
130 T38_FIELD_T4_NON_ECM_SIG_END, | |
131 T38_FIELD_CM_MESSAGE, | |
132 T38_FIELD_JM_MESSAGE, | |
133 T38_FIELD_CI_MESSAGE, | |
134 T38_FIELD_V34RATE | |
135 }; | |
136 | |
137 enum t38_field_classes_e | |
138 { | |
139 T38_FIELD_CLASS_NONE = 0, | |
140 T38_FIELD_CLASS_HDLC, | |
141 T38_FIELD_CLASS_NON_ECM, | |
142 }; | |
143 | |
144 enum t38_message_types_e | |
145 { | |
146 T38_TYPE_OF_MSG_T30_INDICATOR = 0, | |
147 T38_TYPE_OF_MSG_T30_DATA | |
148 }; | |
149 | |
150 enum t38_transport_types_e | |
151 { | |
152 T38_TRANSPORT_UDPTL = 0, | |
153 T38_TRANSPORT_RTP, | |
154 T38_TRANSPORT_TCP | |
155 }; | |
156 | |
157 #define T38_RX_BUF_LEN 2048 | |
158 #define T38_TX_BUF_LEN 16384 | |
159 | |
160 typedef struct | |
161 { | |
162 int numocts; | |
163 const uint8_t *data; | |
164 } asn1_dyn_oct_str_t; | |
165 | |
166 typedef struct | |
167 { | |
168 uint8_t field_data_present; | |
169 unsigned int field_type; | |
170 asn1_dyn_oct_str_t field_data; | |
171 } data_field_element_t; | |
172 | |
173 typedef struct t38_core_state_s t38_core_state_t; | |
174 | |
175 typedef int (t38_tx_packet_handler_t)(t38_core_state_t *s, void *user_data, const uint8_t *buf, int len, int count); | |
176 | |
177 typedef int (t38_rx_indicator_handler_t)(t38_core_state_t *s, void *user_data, int indicator); | |
178 typedef int (t38_rx_data_handler_t)(t38_core_state_t *s, void *user_data, int data_type, int field_type, const uint8_t *buf, int len); | |
179 typedef int (t38_rx_missing_handler_t)(t38_core_state_t *s, void *user_data, int rx_seq_no, int expected_seq_no); | |
180 | |
181 #include <sys/time.h> | |
182 | |
183 /* | |
184 Core T.38 state, common to all modes of T.38. | |
185 */ | |
186 struct t38_core_state_s | |
187 { | |
188 t38_tx_packet_handler_t *tx_packet_handler; | |
189 void *tx_packet_user_data; | |
190 | |
191 t38_rx_indicator_handler_t *rx_indicator_handler; | |
192 t38_rx_data_handler_t *rx_data_handler; | |
193 t38_rx_missing_handler_t *rx_missing_handler; | |
194 void *rx_user_data; | |
195 | |
196 /*! NOTE - Bandwidth reduction shall only be done on suitable Phase C data, i.e., MH, MR | |
197 and - in the case of transcoding to JBIG - MMR. MMR and JBIG require reliable data | |
198 transport such as that provided by TCP. When transcoding is selected, it shall be | |
199 applied to every suitable page in a call. */ | |
200 | |
201 /*! Method 1: Local generation of TCF (required for use with TCP). | |
202 Method 2: Transfer of TCF is required for use with UDP (UDPTL or RTP). | |
203 Method 2 is not recommended for use with TCP. */ | |
204 int data_rate_management_method; | |
205 | |
206 /*! The emitting gateway may indicate a preference for either UDP/UDPTL, or | |
207 UDP/RTP, or TCP for transport of T.38 IFP Packets. The receiving device | |
208 selects the transport protocol. */ | |
209 int data_transport_protocol; | |
210 | |
211 /*! Indicates the capability to remove and insert fill bits in Phase C, non-ECM | |
212 data to reduce bandwidth in the packet network. Optional. See Note. */ | |
213 int fill_bit_removal; | |
214 | |
215 /*! Indicates the ability to convert to/from MMR from/to the line format to | |
216 improve the compression of the data, and reduce the bandwidth, in the | |
217 packet network. Optional. See Note. */ | |
218 int mmr_transcoding; | |
219 | |
220 /*! Indicates the ability to convert to/from JBIG to reduce bandwidth. Optional. | |
221 See Note. */ | |
222 int jbig_transcoding; | |
223 | |
224 /*! For UDP (UDPTL or RTP) modes, this option indicates the maximum | |
225 number of octets that can be stored on the remote device before an overflow | |
226 condition occurs. It is the responsibility of the transmitting application to | |
227 limit the transfer rate to prevent an overflow. The negotiated data rate | |
228 should be used to determine the rate at which data is being removed from | |
229 the buffer. */ | |
230 int max_buffer_size; | |
231 | |
232 /*! This option indicates the maximum size of a UDPTL packet or the | |
233 maximum size of the payload within an RTP packet that can be accepted by | |
234 the remote device. */ | |
235 int max_datagram_size; | |
236 | |
237 /*! This is the version number of ITU-T Rec. T.38. New versions shall be | |
238 compatible with previous versions. */ | |
239 int t38_version; | |
240 | |
241 /*! The fastest data rate supported by the T.38 channel. */ | |
242 int fastest_image_data_rate; | |
243 | |
244 /*! Internet aware FAX (IAF) mode. */ | |
245 int iaf; | |
246 | |
247 int tx_seq_no; | |
248 int rx_expected_seq_no; | |
249 | |
250 int current_rx_indicator; | |
251 int current_tx_indicator; | |
252 | |
253 int missing_packets; | |
254 | |
255 logging_state_t logging; | |
256 }; | |
257 | |
258 #ifdef __cplusplus | |
259 extern "C" { | |
260 #endif | |
261 | |
262 /*! \brief Convert the code for an indicator to a short text name. | |
263 \param indicator The type of indicator. | |
264 \return A pointer to a short text name for the indicator. */ | |
265 const char *t38_indicator(int indicator); | |
266 | |
267 /*! \brief Convert the code for a type of data to a short text name. | |
268 \param data_type The data type. | |
269 \return A pointer to a short text name for the data type. */ | |
270 const char *t38_data_type(int data_type); | |
271 | |
272 /*! \brief Convert the code for a type of data field to a short text name. | |
273 \param field_type The field type. | |
274 \return A pointer to a short text name for the field type. */ | |
275 const char *t38_field_type(int field_type); | |
276 | |
277 int t38_core_send_indicator(t38_core_state_t *s, int indicator, int count); | |
278 | |
279 int t38_core_send_data(t38_core_state_t *s, int data_type, int field_type, const uint8_t *msg, int msglen); | |
280 | |
281 /*! \brief Process a received T.38 IFP packet. | |
282 \param s The T.38 context. | |
283 \param seq_no The packet sequence number. | |
284 \param buf The packet contents. | |
285 \param len The length of the packet contents. | |
286 \return 0 for OK, else -1. */ | |
287 int t38_core_rx_ifp_packet(t38_core_state_t *s, int seq_no, const uint8_t *buf, int len); | |
288 | |
289 /*! Set the method to be used for data rate management, as per the T.38 spec. | |
290 \param s The T.38 context. | |
291 \param method 1 for pass TCF across the T.38 link, 2 for handle TCF locally. | |
292 */ | |
293 void t38_set_data_rate_management_method(t38_core_state_t *s, int method); | |
294 | |
295 /*! Set the data transport protocol. | |
296 \param s The T.38 context. | |
297 \param data_transport_protocol UDPTL, RTP or TPKT. | |
298 */ | |
299 void t38_set_data_transport_protocol(t38_core_state_t *s, int data_transport_protocol); | |
300 | |
301 /*! Set the non-ECM fill bit removal mode. | |
302 \param s The T.38 context. | |
303 \param fill_bit_removal TRUE to remove fill bits across the T.38 link, else FALSE. | |
304 */ | |
305 void t38_set_fill_bit_removal(t38_core_state_t *s, int fill_bit_removal); | |
306 | |
307 /*! Set the MMR transcoding mode. | |
308 \param s The T.38 context. | |
309 \param mmr_transcoding TRUE to transcode to MMR across the T.38 link, else FALSE. | |
310 */ | |
311 void t38_set_mmr_transcoding(t38_core_state_t *s, int mmr_transcoding); | |
312 | |
313 /*! Set the JBIG transcoding mode. | |
314 \param s The T.38 context. | |
315 \param jbig_transcoding TRUE to transcode to JBIG across the T.38 link, else FALSE. | |
316 */ | |
317 void t38_set_jbig_transcoding(t38_core_state_t *s, int jbig_transcoding); | |
318 | |
319 void t38_set_max_buffer_size(t38_core_state_t *s, int max_buffer_size); | |
320 | |
321 void t38_set_max_datagram_size(t38_core_state_t *s, int max_datagram_size); | |
322 | |
323 int t38_get_fastest_image_data_rate(t38_core_state_t *s); | |
324 | |
325 /*! Set the T.38 version to be emulated. | |
326 \param s The T.38 context. | |
327 \param t38_version Version number, as in the T.38 spec. | |
328 */ | |
329 void t38_set_t38_version(t38_core_state_t *s, int t38_version); | |
330 | |
331 t38_core_state_t *t38_core_init(t38_core_state_t *s, | |
332 t38_rx_indicator_handler_t *rx_indicator_handler, | |
333 t38_rx_data_handler_t *rx_data_handler, | |
334 t38_rx_missing_handler_t *rx_missing_handler, | |
335 void *rx_user_data); | |
336 #ifdef __cplusplus | |
337 } | |
338 #endif | |
339 | |
340 #endif | |
341 /*- End of file ------------------------------------------------------------*/ |