Some tweaks to FAX processing
This commit is contained in:
parent
5b4b1dce71
commit
44b01bee6b
|
@ -56,6 +56,7 @@
|
|||
#include "spandsp/alloc.h"
|
||||
#include "spandsp/logging.h"
|
||||
#include "spandsp/bit_operations.h"
|
||||
#include "spandsp/bitstream.h"
|
||||
#include "spandsp/dc_restore.h"
|
||||
#include "spandsp/queue.h"
|
||||
#include "spandsp/power_meter.h"
|
||||
|
@ -73,14 +74,21 @@
|
|||
#include "spandsp/v27ter_rx.h"
|
||||
#include "spandsp/v17tx.h"
|
||||
#include "spandsp/v17rx.h"
|
||||
#if defined(SPANDSP_SUPPORT_V34)
|
||||
#include "spandsp/v34.h"
|
||||
#endif
|
||||
#include "spandsp/super_tone_rx.h"
|
||||
#include "spandsp/modem_connect_tones.h"
|
||||
#include "spandsp/fax_modems.h"
|
||||
|
||||
#include "spandsp/private/logging.h"
|
||||
#include "spandsp/private/bitstream.h"
|
||||
#include "spandsp/private/silence_gen.h"
|
||||
#include "spandsp/private/power_meter.h"
|
||||
#include "spandsp/private/fsk.h"
|
||||
#if defined(SPANDSP_SUPPORT_V34)
|
||||
#include "spandsp/private/v34.h"
|
||||
#endif
|
||||
#include "spandsp/private/v17tx.h"
|
||||
#include "spandsp/private/v17rx.h"
|
||||
#include "spandsp/private/v27ter_tx.h"
|
||||
|
|
|
@ -46,6 +46,9 @@ struct t30_state_s
|
|||
/*! \brief True if behaving as the calling party */
|
||||
bool calling_party;
|
||||
|
||||
/*! \brief True if bad quality pages should be kept */
|
||||
bool keep_bad_pages;
|
||||
|
||||
/*! \brief Internet aware FAX mode bit mask. */
|
||||
int iaf;
|
||||
/*! \brief A bit mask of the currently supported modem types. */
|
||||
|
@ -139,6 +142,15 @@ struct t30_state_s
|
|||
/*! \brief An opaque pointer passed to the transmitted HDLC frame handler. */
|
||||
void *send_hdlc_user_data;
|
||||
|
||||
/*! \brief The document send handler. */
|
||||
t30_document_get_handler_t document_get_handler;
|
||||
/*! \brief An opaque pointer passed to the document send handler. */
|
||||
void *document_get_user_data;
|
||||
/*! \brief The document delivery handler. */
|
||||
t30_document_put_handler_t document_put_handler;
|
||||
/*! \brief An opaque pointer passed to the document delivery handler. */
|
||||
void *document_put_user_data;
|
||||
|
||||
/*! \brief The DIS code for the minimum scan row time we require. This is usually 0ms,
|
||||
but if we are trying to simulate another type of FAX machine, we may need a non-zero
|
||||
value here. */
|
||||
|
|
|
@ -223,6 +223,26 @@ typedef void (*t30_set_handler_t)(void *user_data, int type, int bit_rate, int s
|
|||
*/
|
||||
typedef void (*t30_send_hdlc_handler_t)(void *user_data, const uint8_t msg[], int len);
|
||||
|
||||
/*!
|
||||
T.30 send document handler.
|
||||
\brief T.30 send document handler.
|
||||
\param user_data An opaque pointer.
|
||||
\param msg The document chunk.
|
||||
\param len The length of the chunk.
|
||||
\return The actual length of the chunk.
|
||||
*/
|
||||
typedef int (*t30_document_get_handler_t)(void *user_data, uint8_t msg[], int len);
|
||||
|
||||
/*!
|
||||
T.30 deliver document handler.
|
||||
\brief T.30 deliver handler.
|
||||
\param user_data An opaque pointer.
|
||||
\param msg The document chunk.
|
||||
\param len The length of the chunk.
|
||||
\return The delivery status.
|
||||
*/
|
||||
typedef int (*t30_document_put_handler_t)(void *user_data, const uint8_t msg[], int len);
|
||||
|
||||
/*!
|
||||
T.30 protocol completion codes, at phase E.
|
||||
*/
|
||||
|
|
|
@ -225,6 +225,12 @@ SPAN_DECLARE(const char *) t30_get_tx_password(t30_state_t *s);
|
|||
\return A pointer to the password. */
|
||||
SPAN_DECLARE(const char *) t30_get_rx_password(t30_state_t *s);
|
||||
|
||||
/*! Set the save bad quality pages handling associated with a T.30 context.
|
||||
\brief Set the save bad quality pages handling associated with a T.30 context.
|
||||
\param s The T.30 context.
|
||||
\param keep_bad_pages True to save bad quality pages. */
|
||||
SPAN_DECLARE(void) t30_set_keep_bad_quality_pages(t30_state_t *s, bool keep_bad_pages);
|
||||
|
||||
/*! Set the transmitted TSA (i.e. the one we will send to the far
|
||||
end) associated with a T.30 context.
|
||||
\brief Set the transmitted TSA associated with a T.30 context.
|
||||
|
@ -543,6 +549,10 @@ SPAN_DECLARE(void) t30_set_document_handler(t30_state_t *s, t30_document_handler
|
|||
\param user_data An opaque pointer passed to the callback function. */
|
||||
SPAN_DECLARE(void) t30_set_real_time_frame_handler(t30_state_t *s, t30_real_time_frame_handler_t handler, void *user_data);
|
||||
|
||||
SPAN_DECLARE(void) t30_set_document_get_handler(t30_state_t *s, t30_document_get_handler_t handler, void *user_data);
|
||||
|
||||
SPAN_DECLARE(void) t30_set_document_put_handler(t30_state_t *s, t30_document_put_handler_t handler, void *user_data);
|
||||
|
||||
/*! Get a pointer to the logging context associated with a T.30 context.
|
||||
\brief Get a pointer to the logging context associated with a T.30 context.
|
||||
\param s The T.30 context.
|
||||
|
|
|
@ -785,9 +785,13 @@ static int get_partial_ecm_page(t30_state_t *s)
|
|||
/* These frames contain a frame sequence number within the partial page (one octet) followed
|
||||
by some image data. */
|
||||
s->ecm_data[i][3] = (uint8_t) i;
|
||||
if ((len = t4_tx_get(&s->t4.tx, &s->ecm_data[i][4], s->octets_per_ecm_frame)) < s->octets_per_ecm_frame)
|
||||
if (s->document_get_handler)
|
||||
len = s->document_get_handler(s->document_get_user_data, &s->ecm_data[i][4], s->octets_per_ecm_frame);
|
||||
else
|
||||
len = t4_tx_get(&s->t4.tx, &s->ecm_data[i][4], s->octets_per_ecm_frame);
|
||||
if (len < s->octets_per_ecm_frame)
|
||||
{
|
||||
/* The image is not big enough to fill the entire buffer */
|
||||
/* The document is not big enough to fill the entire buffer */
|
||||
/* We need to pad to a full frame, as most receivers expect that. */
|
||||
if (len > 0)
|
||||
{
|
||||
|
@ -795,7 +799,7 @@ static int get_partial_ecm_page(t30_state_t *s)
|
|||
s->ecm_len[i++] = (int16_t) (s->octets_per_ecm_frame + 4);
|
||||
}
|
||||
s->ecm_frames = i;
|
||||
span_log(&s->logging, SPAN_LOG_FLOW, "Partial page buffer contains %d frames (%d per frame)\n", i, s->octets_per_ecm_frame);
|
||||
span_log(&s->logging, SPAN_LOG_FLOW, "Partial document buffer contains %d frames (%d per frame)\n", i, s->octets_per_ecm_frame);
|
||||
s->ecm_at_page_end = true;
|
||||
return i;
|
||||
}
|
||||
|
@ -2832,6 +2836,7 @@ static int process_rx_pps(t30_state_t *s, const uint8_t *msg, int len)
|
|||
int first_bad_frame;
|
||||
int first;
|
||||
int expected_len;
|
||||
int res;
|
||||
|
||||
if (len < 7)
|
||||
{
|
||||
|
@ -2965,11 +2970,18 @@ static int process_rx_pps(t30_state_t *s, const uint8_t *msg, int len)
|
|||
if (s->rx_ecm_block_ok)
|
||||
{
|
||||
span_log(&s->logging, SPAN_LOG_FLOW, "Partial page OK - committing block %d, %d frames\n", s->ecm_block, s->ecm_frames);
|
||||
/* Deliver the ECM data */
|
||||
for (i = 0; i < s->ecm_frames; i++)
|
||||
{
|
||||
if (t4_rx_put(&s->t4.rx, s->ecm_data[i], s->ecm_len[i]) != T4_DECODE_MORE_DATA)
|
||||
if (s->document_put_handler)
|
||||
res = s->document_put_handler(s->document_put_user_data, s->ecm_data[i], s->ecm_len[i]);
|
||||
else
|
||||
res = t4_rx_put(&s->t4.rx, s->ecm_data[i], s->ecm_len[i]);
|
||||
if (res != T4_DECODE_MORE_DATA)
|
||||
{
|
||||
/* This is the end of the document */
|
||||
if (res != T4_DECODE_OK)
|
||||
span_log(&s->logging, SPAN_LOG_FLOW, "Document ended with status %d\n", res);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
@ -3621,6 +3633,53 @@ static void process_state_f_doc_non_ecm(t30_state_t *s, const uint8_t *msg, int
|
|||
}
|
||||
/*- End of function --------------------------------------------------------*/
|
||||
|
||||
static void assess_copy_quality(t30_state_t *s, uint8_t fcf)
|
||||
{
|
||||
int quality;
|
||||
|
||||
quality = copy_quality(s);
|
||||
switch (quality)
|
||||
{
|
||||
case T30_COPY_QUALITY_PERFECT:
|
||||
case T30_COPY_QUALITY_GOOD:
|
||||
rx_end_page(s);
|
||||
break;
|
||||
case T30_COPY_QUALITY_POOR:
|
||||
rx_end_page(s);
|
||||
break;
|
||||
case T30_COPY_QUALITY_BAD:
|
||||
/* Some people want to keep even the bad pages */
|
||||
if (s->keep_bad_pages)
|
||||
rx_end_page(s);
|
||||
break;
|
||||
}
|
||||
|
||||
if (s->phase_d_handler)
|
||||
s->phase_d_handler(s, s->phase_d_user_data, fcf);
|
||||
if (fcf == T30_EOP)
|
||||
terminate_operation_in_progress(s);
|
||||
else
|
||||
rx_start_page(s);
|
||||
|
||||
switch (quality)
|
||||
{
|
||||
case T30_COPY_QUALITY_PERFECT:
|
||||
case T30_COPY_QUALITY_GOOD:
|
||||
set_state(s, T30_STATE_III_Q_MCF);
|
||||
send_simple_frame(s, T30_MCF);
|
||||
break;
|
||||
case T30_COPY_QUALITY_POOR:
|
||||
set_state(s, T30_STATE_III_Q_RTP);
|
||||
send_simple_frame(s, T30_RTP);
|
||||
break;
|
||||
case T30_COPY_QUALITY_BAD:
|
||||
set_state(s, T30_STATE_III_Q_RTN);
|
||||
send_simple_frame(s, T30_RTN);
|
||||
break;
|
||||
}
|
||||
}
|
||||
/*- End of function --------------------------------------------------------*/
|
||||
|
||||
static void process_state_f_post_doc_non_ecm(t30_state_t *s, const uint8_t *msg, int len)
|
||||
{
|
||||
uint8_t fcf;
|
||||
|
@ -3636,33 +3695,7 @@ static void process_state_f_post_doc_non_ecm(t30_state_t *s, const uint8_t *msg,
|
|||
case T30_MPS:
|
||||
s->next_rx_step = fcf;
|
||||
queue_phase(s, T30_PHASE_D_TX);
|
||||
switch (copy_quality(s))
|
||||
{
|
||||
case T30_COPY_QUALITY_PERFECT:
|
||||
case T30_COPY_QUALITY_GOOD:
|
||||
rx_end_page(s);
|
||||
if (s->phase_d_handler)
|
||||
s->phase_d_handler(s, s->phase_d_user_data, fcf);
|
||||
rx_start_page(s);
|
||||
set_state(s, T30_STATE_III_Q_MCF);
|
||||
send_simple_frame(s, T30_MCF);
|
||||
break;
|
||||
case T30_COPY_QUALITY_POOR:
|
||||
rx_end_page(s);
|
||||
if (s->phase_d_handler)
|
||||
s->phase_d_handler(s, s->phase_d_user_data, fcf);
|
||||
rx_start_page(s);
|
||||
set_state(s, T30_STATE_III_Q_RTP);
|
||||
send_simple_frame(s, T30_RTP);
|
||||
break;
|
||||
case T30_COPY_QUALITY_BAD:
|
||||
if (s->phase_d_handler)
|
||||
s->phase_d_handler(s, s->phase_d_user_data, fcf);
|
||||
rx_start_page(s);
|
||||
set_state(s, T30_STATE_III_Q_RTN);
|
||||
send_simple_frame(s, T30_RTN);
|
||||
break;
|
||||
}
|
||||
assess_copy_quality(s, fcf);
|
||||
break;
|
||||
case T30_PRI_EOM:
|
||||
if (s->remote_interrupts_allowed)
|
||||
|
@ -3674,33 +3707,7 @@ static void process_state_f_post_doc_non_ecm(t30_state_t *s, const uint8_t *msg,
|
|||
s->next_rx_step = fcf;
|
||||
/* Return to phase B */
|
||||
queue_phase(s, T30_PHASE_B_TX);
|
||||
switch (copy_quality(s))
|
||||
{
|
||||
case T30_COPY_QUALITY_PERFECT:
|
||||
case T30_COPY_QUALITY_GOOD:
|
||||
rx_end_page(s);
|
||||
if (s->phase_d_handler)
|
||||
s->phase_d_handler(s, s->phase_d_user_data, fcf);
|
||||
rx_start_page(s);
|
||||
set_state(s, T30_STATE_III_Q_MCF);
|
||||
send_simple_frame(s, T30_MCF);
|
||||
break;
|
||||
case T30_COPY_QUALITY_POOR:
|
||||
rx_end_page(s);
|
||||
if (s->phase_d_handler)
|
||||
s->phase_d_handler(s, s->phase_d_user_data, fcf);
|
||||
rx_start_page(s);
|
||||
set_state(s, T30_STATE_III_Q_RTP);
|
||||
send_simple_frame(s, T30_RTP);
|
||||
break;
|
||||
case T30_COPY_QUALITY_BAD:
|
||||
if (s->phase_d_handler)
|
||||
s->phase_d_handler(s, s->phase_d_user_data, fcf);
|
||||
rx_start_page(s);
|
||||
set_state(s, T30_STATE_III_Q_RTN);
|
||||
send_simple_frame(s, T30_RTN);
|
||||
break;
|
||||
}
|
||||
assess_copy_quality(s, fcf);
|
||||
break;
|
||||
case T30_PRI_EOP:
|
||||
if (s->remote_interrupts_allowed)
|
||||
|
@ -3712,37 +3719,7 @@ static void process_state_f_post_doc_non_ecm(t30_state_t *s, const uint8_t *msg,
|
|||
s->end_of_procedure_detected = true;
|
||||
s->next_rx_step = fcf;
|
||||
queue_phase(s, T30_PHASE_D_TX);
|
||||
switch (copy_quality(s))
|
||||
{
|
||||
case T30_COPY_QUALITY_PERFECT:
|
||||
case T30_COPY_QUALITY_GOOD:
|
||||
rx_end_page(s);
|
||||
if (s->phase_d_handler)
|
||||
s->phase_d_handler(s, s->phase_d_user_data, fcf);
|
||||
terminate_operation_in_progress(s);
|
||||
set_state(s, T30_STATE_III_Q_MCF);
|
||||
send_simple_frame(s, T30_MCF);
|
||||
break;
|
||||
case T30_COPY_QUALITY_POOR:
|
||||
rx_end_page(s);
|
||||
if (s->phase_d_handler)
|
||||
s->phase_d_handler(s, s->phase_d_user_data, fcf);
|
||||
terminate_operation_in_progress(s);
|
||||
set_state(s, T30_STATE_III_Q_RTP);
|
||||
send_simple_frame(s, T30_RTP);
|
||||
break;
|
||||
case T30_COPY_QUALITY_BAD:
|
||||
#if 0
|
||||
/* Some people want to keep even the bad pages */
|
||||
if (s->keep_bad_pages)
|
||||
rx_end_page(s);
|
||||
#endif
|
||||
if (s->phase_d_handler)
|
||||
s->phase_d_handler(s, s->phase_d_user_data, fcf);
|
||||
set_state(s, T30_STATE_III_Q_RTN);
|
||||
send_simple_frame(s, T30_RTN);
|
||||
break;
|
||||
}
|
||||
assess_copy_quality(s, fcf);
|
||||
break;
|
||||
case T30_DCN:
|
||||
t30_set_status(s, T30_ERR_RX_DCNFAX);
|
||||
|
@ -5806,6 +5783,7 @@ static void t30_non_ecm_rx_status(void *user_data, int status)
|
|||
SPAN_DECLARE_NONSTD(void) t30_non_ecm_put_bit(void *user_data, int bit)
|
||||
{
|
||||
t30_state_t *s;
|
||||
int res;
|
||||
|
||||
if (bit < 0)
|
||||
{
|
||||
|
@ -5830,10 +5808,12 @@ SPAN_DECLARE_NONSTD(void) t30_non_ecm_put_bit(void *user_data, int bit)
|
|||
}
|
||||
break;
|
||||
case T30_STATE_F_DOC_NON_ECM:
|
||||
/* Document transfer */
|
||||
if (t4_rx_put_bit(&s->t4.rx, bit) != T4_DECODE_MORE_DATA)
|
||||
/* Image transfer */
|
||||
if ((res = t4_rx_put_bit(&s->t4.rx, bit)) != T4_DECODE_MORE_DATA)
|
||||
{
|
||||
/* That is the end of the document */
|
||||
/* This is the end of the image */
|
||||
if (res != T4_DECODE_OK)
|
||||
span_log(&s->logging, SPAN_LOG_FLOW, "Page ended with status %d\n", res);
|
||||
set_state(s, T30_STATE_F_POST_DOC_NON_ECM);
|
||||
queue_phase(s, T30_PHASE_D_RX);
|
||||
timer_t2_start(s);
|
||||
|
@ -5847,6 +5827,7 @@ SPAN_DECLARE(void) t30_non_ecm_put(void *user_data, const uint8_t buf[], int len
|
|||
{
|
||||
t30_state_t *s;
|
||||
int i;
|
||||
int res;
|
||||
|
||||
s = (t30_state_t *) user_data;
|
||||
switch (s->state)
|
||||
|
@ -5870,10 +5851,12 @@ SPAN_DECLARE(void) t30_non_ecm_put(void *user_data, const uint8_t buf[], int len
|
|||
}
|
||||
break;
|
||||
case T30_STATE_F_DOC_NON_ECM:
|
||||
/* Document transfer */
|
||||
if (t4_rx_put(&s->t4.rx, buf, len) != T4_DECODE_MORE_DATA)
|
||||
/* Image transfer */
|
||||
if ((res = t4_rx_put(&s->t4.rx, buf, len)) != T4_DECODE_MORE_DATA)
|
||||
{
|
||||
/* That is the end of the document */
|
||||
/* This is the end of the image */
|
||||
if (res != T4_DECODE_OK)
|
||||
span_log(&s->logging, SPAN_LOG_FLOW, "Page ended with status %d\n", res);
|
||||
set_state(s, T30_STATE_F_POST_DOC_NON_ECM);
|
||||
queue_phase(s, T30_PHASE_D_RX);
|
||||
timer_t2_start(s);
|
||||
|
|
|
@ -648,6 +648,12 @@ SPAN_DECLARE(int) t30_set_ecm_capability(t30_state_t *s, bool enabled)
|
|||
}
|
||||
/*- End of function --------------------------------------------------------*/
|
||||
|
||||
SPAN_DECLARE(void) t30_set_keep_bad_quality_pages(t30_state_t *s, bool keep_bad_pages)
|
||||
{
|
||||
s->keep_bad_pages = keep_bad_pages;
|
||||
}
|
||||
/*- End of function --------------------------------------------------------*/
|
||||
|
||||
SPAN_DECLARE(int) t30_set_supported_output_compressions(t30_state_t *s, int supported_compressions)
|
||||
{
|
||||
/* Mask out the ones we actually support today. */
|
||||
|
@ -859,6 +865,20 @@ SPAN_DECLARE(void) t30_set_real_time_frame_handler(t30_state_t *s, t30_real_time
|
|||
}
|
||||
/*- End of function --------------------------------------------------------*/
|
||||
|
||||
SPAN_DECLARE(void) t30_set_document_get_handler(t30_state_t *s, t30_document_get_handler_t handler, void *user_data)
|
||||
{
|
||||
s->document_get_handler = handler;
|
||||
s->document_get_user_data = user_data;
|
||||
}
|
||||
/*- End of function --------------------------------------------------------*/
|
||||
|
||||
SPAN_DECLARE(void) t30_set_document_put_handler(t30_state_t *s, t30_document_put_handler_t handler, void *user_data)
|
||||
{
|
||||
s->document_put_handler = handler;
|
||||
s->document_put_user_data = user_data;
|
||||
}
|
||||
/*- End of function --------------------------------------------------------*/
|
||||
|
||||
SPAN_DECLARE(logging_state_t *) t30_get_logging_state(t30_state_t *s)
|
||||
{
|
||||
return &s->logging;
|
||||
|
|
|
@ -927,7 +927,7 @@ static int read_tiff_t85_image(t4_tx_state_t *s)
|
|||
pack.row = 0;
|
||||
t85_decode_init(&t85, packing_row_write_handler, &pack);
|
||||
t85_decode_set_comment_handler(&t85, 1000, embedded_comment_handler, s);
|
||||
|
||||
t85_decode_set_image_size_constraints(&t85, s->tiff.image_width, s->tiff.image_length);
|
||||
result = -1;
|
||||
for (i = 0; i < num_strips; i++)
|
||||
{
|
||||
|
@ -938,8 +938,7 @@ static int read_tiff_t85_image(t4_tx_state_t *s)
|
|||
span_free(raw_data);
|
||||
return -1;
|
||||
}
|
||||
result = t85_decode_put(&t85, raw_data, len);
|
||||
if (result != T4_DECODE_MORE_DATA)
|
||||
if ((result = t85_decode_put(&t85, raw_data, len)) != T4_DECODE_MORE_DATA)
|
||||
break;
|
||||
}
|
||||
if (result == T4_DECODE_MORE_DATA)
|
||||
|
@ -1000,6 +999,7 @@ static int read_tiff_t43_image(t4_tx_state_t *s)
|
|||
|
||||
t43_decode_init(&t43, packing_row_write_handler, &pack);
|
||||
t43_decode_set_comment_handler(&t43, 1000, embedded_comment_handler, NULL);
|
||||
t43_decode_set_image_size_constraints(&t43, s->tiff.image_width, s->tiff.image_length);
|
||||
logging = t43_decode_get_logging_state(&t43);
|
||||
span_log_set_level(logging, SPAN_LOG_SHOW_SEVERITY | SPAN_LOG_SHOW_PROTOCOL | SPAN_LOG_FLOW);
|
||||
|
||||
|
@ -1018,8 +1018,7 @@ static int read_tiff_t43_image(t4_tx_state_t *s)
|
|||
span_free(raw_data);
|
||||
return -1;
|
||||
}
|
||||
result = t43_decode_put(&t43, raw_data, len);
|
||||
if (result != T4_DECODE_MORE_DATA)
|
||||
if ((result = t43_decode_put(&t43, raw_data, len)) != T4_DECODE_MORE_DATA)
|
||||
break;
|
||||
}
|
||||
if (result == T4_DECODE_MORE_DATA)
|
||||
|
|
|
@ -31,7 +31,6 @@
|
|||
#else
|
||||
#if defined(__APPLE__)
|
||||
#include <util.h>
|
||||
#include <sys/ioctl.h>
|
||||
#elif defined(__FreeBSD__)
|
||||
#include <libutil.h>
|
||||
#include <termios.h>
|
||||
|
@ -39,6 +38,8 @@
|
|||
#else
|
||||
#include <pty.h>
|
||||
#endif
|
||||
#include <sys/ioctl.h>
|
||||
#include <fcntl.h>
|
||||
#include <unistd.h>
|
||||
#include <errno.h>
|
||||
#include <fcntl.h>
|
||||
|
@ -62,9 +63,6 @@ static int master(void)
|
|||
char buf[1024];
|
||||
int len;
|
||||
int i;
|
||||
#if !defined(WIN32)
|
||||
int tioflags;
|
||||
#endif
|
||||
|
||||
for (i = 0; i < 10; i++)
|
||||
{
|
||||
|
@ -76,15 +74,6 @@ static int master(void)
|
|||
printf("%s %s\n", modem[i].devlink, modem[i].stty);
|
||||
}
|
||||
|
||||
for (i = 0; i < 10; i++)
|
||||
{
|
||||
#if !defined(WIN32)
|
||||
ioctl(modem[i].slave, TIOCMGET, &tioflags);
|
||||
tioflags |= TIOCM_RI;
|
||||
ioctl(modem[i].slave, TIOCMSET, &tioflags);
|
||||
#endif
|
||||
}
|
||||
|
||||
for (;;)
|
||||
{
|
||||
for (i = 0; i < 10; i++)
|
||||
|
@ -94,11 +83,6 @@ static int master(void)
|
|||
{
|
||||
buf[len] = '\0';
|
||||
printf("%d %d '%s' %s\n", i, len, buf, strerror(errno));
|
||||
#if !defined(WIN32)
|
||||
ioctl(modem[i].slave, TIOCMGET, &tioflags);
|
||||
tioflags |= TIOCM_RI;
|
||||
ioctl(modem[i].slave, TIOCMSET, &tioflags);
|
||||
#endif
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -121,9 +105,6 @@ static int slave(void)
|
|||
char name[64];
|
||||
int i;
|
||||
int j;
|
||||
#if !defined(WIN32)
|
||||
int tioflags;
|
||||
#endif
|
||||
|
||||
for (i = 0; i < 10; i++)
|
||||
{
|
||||
|
@ -136,27 +117,11 @@ static int slave(void)
|
|||
printf("%s\n", name);
|
||||
}
|
||||
|
||||
for (i = 0; i < 10; i++)
|
||||
{
|
||||
#if !defined(WIN32)
|
||||
ioctl(fd[i], TIOCMGET, &tioflags);
|
||||
if ((tioflags & TIOCM_RI))
|
||||
printf("Ring %d\n", i);
|
||||
else
|
||||
printf("No ring %d\n", i);
|
||||
#endif
|
||||
}
|
||||
|
||||
for (j = 0; j < 10; j++)
|
||||
{
|
||||
for (i = 0; i < 10; i++)
|
||||
{
|
||||
write(fd[i], "FRED", 4);
|
||||
#if !defined(WIN32)
|
||||
ioctl(fd[i], TIOCMGET, &tioflags);
|
||||
if ((tioflags & TIOCM_RI))
|
||||
printf("Ring %d\n", i);
|
||||
#endif
|
||||
}
|
||||
}
|
||||
|
||||
|
|
Loading…
Reference in New Issue