Browse Source

tpws: specify oob byte . tamper pos range limiter

pull/176/head
bol-van 1 year ago
parent
commit
663a2bb2a4
  1. BIN
      binaries/aarch64/tpws
  2. BIN
      binaries/arm/tpws
  3. BIN
      binaries/freebsd-x64/tpws
  4. BIN
      binaries/mac64/tpws
  5. BIN
      binaries/mips32r1-lsb/tpws
  6. BIN
      binaries/mips32r1-msb/tpws
  7. BIN
      binaries/mips64r2-msb/tpws
  8. BIN
      binaries/ppc/tpws
  9. BIN
      binaries/x86/tpws
  10. BIN
      binaries/x86_64/tpws
  11. BIN
      binaries/x86_64/tpws_wsl.tgz
  12. 3
      tpws/params.h
  13. 34
      tpws/tpws.c
  14. 32
      tpws/tpws_conn.c

BIN
binaries/aarch64/tpws

Binary file not shown.

BIN
binaries/arm/tpws

Binary file not shown.

BIN
binaries/freebsd-x64/tpws

Binary file not shown.

BIN
binaries/mac64/tpws

Binary file not shown.

BIN
binaries/mips32r1-lsb/tpws

Binary file not shown.

BIN
binaries/mips32r1-msb/tpws

Binary file not shown.

BIN
binaries/mips64r2-msb/tpws

Binary file not shown.

BIN
binaries/ppc/tpws

Binary file not shown.

BIN
binaries/x86/tpws

Binary file not shown.

BIN
binaries/x86_64/tpws

Binary file not shown.

BIN
binaries/x86_64/tpws_wsl.tgz

Binary file not shown.

3
tpws/params.h

@ -50,6 +50,7 @@ struct params_s
bool split_any_protocol; bool split_any_protocol;
int split_pos; int split_pos;
bool disorder, oob; bool disorder, oob;
uint8_t oob_byte;
int ttl_default; int ttl_default;
char pidfile[256]; char pidfile[256];
@ -60,6 +61,8 @@ struct params_s
int hostlist_auto_fail_threshold, hostlist_auto_fail_time; int hostlist_auto_fail_threshold, hostlist_auto_fail_time;
hostfail_pool *hostlist_auto_fail_counters; hostfail_pool *hostlist_auto_fail_counters;
unsigned int tamper_start,tamper_cutoff;
int debug; int debug;
#if defined(BSD) #if defined(BSD)

34
tpws/tpws.c

@ -176,7 +176,7 @@ static void exithelp(void)
#else #else
" --disorder\t\t\t\t; when splitting simulate sending second fragment first\n" " --disorder\t\t\t\t; when splitting simulate sending second fragment first\n"
#endif #endif
" --oob\t\t\t\t\t; when splitting send out of band zero byte\n" " --oob[=<char>|0xHEX]\t\t\t; when splitting send out of band byte. default is HEX 0x00.\n"
" --hostcase\t\t\t\t; change Host: => host:\n" " --hostcase\t\t\t\t; change Host: => host:\n"
" --hostspell\t\t\t\t; exact spelling of \"Host\" header. must be 4 chars. default is \"host\"\n" " --hostspell\t\t\t\t; exact spelling of \"Host\" header. must be 4 chars. default is \"host\"\n"
" --hostdot\t\t\t\t; add \".\" after Host: name\n" " --hostdot\t\t\t\t; add \".\" after Host: name\n"
@ -188,7 +188,9 @@ static void exithelp(void)
" --methodeol\t\t\t\t; add end-of-line before method\n" " --methodeol\t\t\t\t; add end-of-line before method\n"
" --unixeol\t\t\t\t; replace 0D0A to 0A\n" " --unixeol\t\t\t\t; replace 0D0A to 0A\n"
" --tlsrec=sni\t\t\t\t; make 2 TLS records. split at SNI. don't split if SNI is not present\n" " --tlsrec=sni\t\t\t\t; make 2 TLS records. split at SNI. don't split if SNI is not present\n"
" --tlsrec-pos=<pos>\t\t\t; make 2 TLS records. split at specified pos\n", " --tlsrec-pos=<pos>\t\t\t; make 2 TLS records. split at specified pos\n"
" --tamper-start=<pos>\t\t\t; start tampering only from specified outbound stream position. default is 0.\n"
" --tamper-cutoff=<pos>\t\t\t; do not tamper anymore after specified outbound stream position. default is unlimited.\n",
HOSTLIST_AUTO_FAIL_THRESHOLD_DEFAULT, HOSTLIST_AUTO_FAIL_TIME_DEFAULT HOSTLIST_AUTO_FAIL_THRESHOLD_DEFAULT, HOSTLIST_AUTO_FAIL_TIME_DEFAULT
); );
exit(1); exit(1);
@ -295,7 +297,7 @@ void parse_params(int argc, char *argv[])
{ "split-pos",required_argument,0,0 },// optidx=24 { "split-pos",required_argument,0,0 },// optidx=24
{ "split-any-protocol",optional_argument,0,0},// optidx=25 { "split-any-protocol",optional_argument,0,0},// optidx=25
{ "disorder",no_argument,0,0 },// optidx=26 { "disorder",no_argument,0,0 },// optidx=26
{ "oob",no_argument,0,0 },// optidx=27 { "oob",optional_argument,0,0 },// optidx=27
{ "methodspace",no_argument,0,0 },// optidx=28 { "methodspace",no_argument,0,0 },// optidx=28
{ "methodeol",no_argument,0,0 },// optidx=29 { "methodeol",no_argument,0,0 },// optidx=29
{ "hosttab",no_argument,0,0 },// optidx=30 { "hosttab",no_argument,0,0 },// optidx=30
@ -317,8 +319,10 @@ void parse_params(int argc, char *argv[])
{ "socks",no_argument,0,0 },// optidx=46 { "socks",no_argument,0,0 },// optidx=46
{ "no-resolve",no_argument,0,0 },// optidx=47 { "no-resolve",no_argument,0,0 },// optidx=47
{ "skip-nodelay",no_argument,0,0 },// optidx=48 { "skip-nodelay",no_argument,0,0 },// optidx=48
{ "tamper-start",required_argument,0,0 },// optidx=49
{ "tamper-cutoff",required_argument,0,0 },// optidx=50
#if defined(BSD) && !defined(__OpenBSD__) && !defined(__APPLE__) #if defined(BSD) && !defined(__OpenBSD__) && !defined(__APPLE__)
{ "enable-pf",no_argument,0,0 },// optidx=49 { "enable-pf",no_argument,0,0 },// optidx=51
#endif #endif
{ "hostlist-auto-retrans-threshold",optional_argument,0,0}, // ignored. for nfqws command line compatibility { "hostlist-auto-retrans-threshold",optional_argument,0,0}, // ignored. for nfqws command line compatibility
{ NULL,0,NULL,0 } { NULL,0,NULL,0 }
@ -508,6 +512,18 @@ void parse_params(int argc, char *argv[])
save_default_ttl(); save_default_ttl();
break; break;
case 27: /* oob */ case 27: /* oob */
if (optarg)
{
size_t l = strlen(optarg);
unsigned int bt;
if (l==1) params.oob_byte = (uint8_t)*optarg;
else if (l!=4 || sscanf(optarg,"0x%02X",&bt)!=1)
{
fprintf(stderr, "Invalid argument for oob\n");
exit_clean(1);
}
else params.oob_byte = (uint8_t)bt;
}
params.oob = true; params.oob = true;
break; break;
case 28: /* methodspace */ case 28: /* methodspace */
@ -653,8 +669,14 @@ void parse_params(int argc, char *argv[])
case 48: /* skip-nodelay */ case 48: /* skip-nodelay */
params.skip_nodelay = true; params.skip_nodelay = true;
break; break;
case 49: /* tamper-start */
params.tamper_start = atoi(optarg);
break;
case 50: /* tamper-cutoff */
params.tamper_cutoff = atoi(optarg);
break;
#if defined(BSD) && !defined(__OpenBSD__) && !defined(__APPLE__) #if defined(BSD) && !defined(__OpenBSD__) && !defined(__APPLE__)
case 49: /* enable-pf */ case 51: /* enable-pf */
params.pf_enable = true; params.pf_enable = true;
break; break;
#endif #endif
@ -798,7 +820,7 @@ static bool set_ulimit(void)
// additional 1/2 for unpaired remote legs sending buffers // additional 1/2 for unpaired remote legs sending buffers
// 16 for listen_fd, epoll, hostlist, ... // 16 for listen_fd, epoll, hostlist, ...
#ifdef SPLICE_PRESENT #ifdef SPLICE_PRESENT
fdmax = (params.tamper ? 4 : 6) * params.maxconn; fdmax = (params.tamper && !params.tamper_start && !params.tamper_cutoff ? 4 : 6) * params.maxconn;
#else #else
fdmax = 2 * params.maxconn; fdmax = 2 * params.maxconn;
#endif #endif

32
tpws/tpws_conn.c

@ -400,7 +400,7 @@ static tproxy_conn_t *new_conn(int fd, bool remote)
#ifdef SPLICE_PRESENT #ifdef SPLICE_PRESENT
// if dont tamper - both legs are spliced, create 2 pipes // if dont tamper - both legs are spliced, create 2 pipes
// otherwise create pipe only in local leg // otherwise create pipe only in local leg
if((!params.tamper || !remote) && pipe2(conn->splice_pipe, O_NONBLOCK) != 0) if ((!remote || !params.tamper || params.tamper_start || params.tamper_cutoff ) && pipe2(conn->splice_pipe, O_NONBLOCK) != 0)
{ {
fprintf(stderr, "Could not create the splice pipe\n"); fprintf(stderr, "Could not create the splice pipe\n");
free_conn(conn); free_conn(conn);
@ -905,10 +905,13 @@ static void tamper(tproxy_conn_t *conn, uint8_t *segment, size_t segment_buffer_
tamper_in(&conn->partner->track,segment,segment_buffer_size,segment_size); tamper_in(&conn->partner->track,segment,segment_buffer_size,segment_size);
} }
} }
else else if (conn->trd >= params.tamper_start && (!params.tamper_cutoff || conn->trd < params.tamper_cutoff))
{ {
DBGPRINT("tamper_out stream pos %zu. tamper range %u-%u", conn->trd, params.tamper_start, params.tamper_cutoff)
tamper_out(&conn->track,segment,segment_buffer_size,segment_size,split_pos); tamper_out(&conn->track,segment,segment_buffer_size,segment_size,split_pos);
} }
else
DBGPRINT("stream pos %zu is out of tamper range %u-%u", conn->trd, params.tamper_start, params.tamper_cutoff)
} }
} }
@ -963,8 +966,13 @@ static bool handle_epoll(tproxy_conn_t *conn, struct tailhead *conn_list, uint32
DBGPRINT("numbytes=%d",numbytes) DBGPRINT("numbytes=%d",numbytes)
if (numbytes>0) if (numbytes>0)
{ {
if (conn->remote)
VPRINT("remote leg stream pos R/W : %zu/%zu",conn->trd,conn->twr)
else
VPRINT("local leg stream pos : %zu/%zu",conn->trd,conn->twr)
#ifdef SPLICE_PRESENT #ifdef SPLICE_PRESENT
if (!params.tamper || conn->remote && conn->partner->track.bTamperInCutoff) if (!params.tamper || conn->remote && conn->partner->track.bTamperInCutoff ||
!conn->remote && (conn->trd < params.tamper_start || params.tamper_cutoff && conn->trd >= params.tamper_cutoff))
{ {
// incoming data from remote leg we splice without touching // incoming data from remote leg we splice without touching
// pipe is in the local leg, so its in conn->partner->splice_pipe // pipe is in the local leg, so its in conn->partner->splice_pipe
@ -998,26 +1006,28 @@ static bool handle_epoll(tproxy_conn_t *conn, struct tailhead *conn_list, uint32
if (rd<0 && errno==EAGAIN) rd=0; if (rd<0 && errno==EAGAIN) rd=0;
if (rd>0) if (rd>0)
{ {
conn->trd+=rd;
size_t split_pos; size_t split_pos;
bs = rd; bs = rd;
// tamper needs to know stream position of the block start
tamper(conn, buf, sizeof(buf), &bs, &split_pos); tamper(conn, buf, sizeof(buf), &bs, &split_pos);
// increase after tamper
conn->trd+=rd;
if (split_pos) if (split_pos)
{ {
uint8_t oob;
VPRINT("Splitting at pos %zu", split_pos) VPRINT("Splitting at pos %zu", split_pos)
if (params.oob) if (params.oob)
{ {
oob = buf[split_pos]; uint8_t oob_save;
buf[split_pos] = 0; oob_save = buf[split_pos];
buf[split_pos] = params.oob_byte;
wr = send_or_buffer(conn->partner->wr_buf, conn->partner->fd, buf, split_pos+1, MSG_OOB, params.disorder ? 1 : 0);
buf[split_pos] = oob_save;
} }
wr = send_or_buffer(conn->partner->wr_buf, conn->partner->fd, buf, split_pos+1, params.oob ? MSG_OOB : 0, params.disorder ? 1 : 0); else
if (params.oob) buf[split_pos] = oob; wr = send_or_buffer(conn->partner->wr_buf, conn->partner->fd, buf, split_pos, 0, params.disorder ? 1 : 0);
DBGPRINT("send_or_buffer(1) fd=%d wr=%zd err=%d",conn->partner->fd,wr,errno) DBGPRINT("send_or_buffer(1) fd=%d wr=%zd err=%d",conn->partner->fd,wr,errno)
if (wr >= 0) if (wr >= 0)
{ {

Loading…
Cancel
Save