• No results found

User-space applications can request that a specific HICCUPS coverage type be used for their connection by issuing a setsockopt() call prior to opening the connection. List- ing 7.1 shows an example connection attempt where an application specifies its desired HICCUPS coverage type (see Section 5.5 for a list of coverages to which cvr can be set).

Listing 7.1: Requesting a coverage type sockfd = socket(...);

setsockopt(sockfd, SOL_TCP, TCP_HICCUPS_COVERAGE, &cvr,

sizeof (cvr)); connect(sockfd, ...);

write(sockfd, msg, msglen); close(sockfd);

Similarly, once a connection has been established an application can read the results of the HICCUPS integrity checks by issuing some calls to getsockopt(). A total of three calls to getsockopt() are required in order to retrieve all status values: the overall HICCUPS match status, the SYN match bits, and the SYN-ACK match bits. Listing 7.2 shows some example connection code.

Listing 7.2: Retrieving the HICCUPS status of a connection sockfd = socket(...);

connect(sockfd, ...);

write(sockfd, msg, msglen);

getsockopt(sockfd, SOL_TCP, TCP_HICCUPS_STATUS, &result1, &result1_len);

getsockopt(sockfd, SOL_TCP, TCP_HICCUPS_SYN_MATCH, &result2, &result2_len);

getsockopt(sockfd, SOL_TCP, TCP_HICCUPS_SYNACK_MATCH, &result3, &result3_len);

close(sockfd);

AppSalt

As we detailed in Chapter 6, AppSalt is an optional layer of protection that requires the ker- nel to know the initial byte range of data that an application wishes to send in a connection before the TCP 3WHS is initiated. This situation is incompatible with the traditional order- ing of Linux socket calls as shown in Listing 7.3. In that sequence of calls, the TCP 3WHS is initiated by the connect() call, and the SYN is sent before the kernel is presented with any application data.

Fortunately, this problem has already been approached in Linux and a good parallel exists for requiring data at the time of connection initiation, TCP Fast Open (TFO). TFO [23] is a TCP enhancement that allows follow-up connections between two endpoints to not have to wait for the full 3WHS to complete. If two TFO-enabled TCPs have communicated previously, they shared a TFO cookie (a cryptographic token sent in a new TCP option kind) that can be sent with subsequent connections to authorize immediate data transmission and save the latency cost of the additional RTT spent waiting for the SYN-ACK to be received. Programs that use TFO initiate all connections using sendto() or sendmsg() with the MSG_FASTOPENflag, as opposed to the typical connect() and send() sequence. In this way, the kernel can embed data in the SYN for connections with a valid TFO cookie. We therefore leverage the same socket API changes as TFO to allow a client program to request AppSalt-mode HICCUPS. Primarily, we add a new message flag within the

framework established by TFO that can be used by the sendto() call: “MSG_HICCUPS.” Listing 7.4 shows the new sequence of calls that applications use in order to request AppSalt protection. Note that now there is no connect() call required for socket setup. As soon as an application wants to send data it issues the sendto() and all of the AppSalt logic along with TCP connection setup happens behind the scenes in the kernel.

Listing 7.3: Old socket call order

s = s o c k e t ( . . . ) ; c o n n e c t ( s , a d d r ) ; s e n d ( s , msg ) ;

Listing 7.4: New socket call order

s = s o c k e t ( . . . ) ; s e n d t o ( s , msg ,

MSG_HICCUPS , a d d r ) ;

As an added benefit of the TFO-style approach, the addition of HICCUPS support is trivial for applications that already support TFO (e.g., Google Chrome [115]). Since we use the same calling method as TFO with just a different flag name, it is trivial for applications that already use TFO to also use AppSalt protection with HICCUPS. The application need only OR the MSG_HICCUPS flag with the MSG_FASTOPEN flag in its sendto() calls, as shown in Listing 7.5. Any time that application data cannot be used (i.e., a program does not use the new socket API or it is a TFO connection with data in the SYN) the ISN contains an integrity value without the application-layer obfuscation (as in Figure 5.1).

Listing 7.5: TCP Fast Open with HICCUPS

s = s o c k e t ( . . . ) ;

s e n d t o ( s , msg , MSG_FASTOPEN | MSG_HICCUPS , a d d r ) ;

An alternate strategy that could be used to implement AppSalt would be to instead modify the kernel API logic behind the connect() call so that the 3WHS is not initiated until the first send() call. This change would have the positive property of automatically en- gaging AppSalt protection for all applications without having to update them, but concerns about compatibility and decreased acceptance by the community led us to opt for the more gradual approach. We also desire the approach that gives the application designer more ex- plicit control in case there is some unforeseen problem with delaying connection initiation.

Given the firmly established history and wide understanding of socket calls, we believe the best method of implementing AppSalt is the TFO-style approach.

Finally, we feel it is important to reiterate that normal HICCUPS as presented in Chap- ter 5 works fine for all connections in Linux without any of the previously described API changes. All of these changes are to enable the AppSalt enhanced protection mode as de- scribed in Chapter 6. When an application does not support the MSG_HICCUPS flag, we emphasize that nothing breaks, the only result is that that application’s connections use the regular HICCUPS without the additional ephemeral secret protection.