Skip to content
GitLab
Menu
Projects
Groups
Snippets
/
Help
Help
Support
Community forum
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in
Toggle navigation
Menu
Open sidebar
The Tor Project
Core
Tor
Commits
9ca1af9a
Commit
9ca1af9a
authored
Sep 07, 2018
by
Nick Mathewson
⛰
Browse files
Merge remote-tracking branch 'dgoulet/ticket20700_035_03'
parents
13d0855a
3695ef63
Changes
20
Expand all
Hide whitespace changes
Inline
Side-by-side
src/app/config/config.c
View file @
9ca1af9a
...
...
@@ -459,6 +459,7 @@ static config_var_t option_vars_[] = {
VAR
(
"HiddenServiceNumIntroductionPoints"
,
LINELIST_S
,
RendConfigLines
,
NULL
),
VAR
(
"HiddenServiceStatistics"
,
BOOL
,
HiddenServiceStatistics_option
,
"1"
),
V
(
HidServAuth
,
LINELIST
,
NULL
),
V
(
ClientOnionAuthDir
,
FILENAME
,
NULL
),
OBSOLETE
(
"CloseHSClientCircuitsImmediatelyOnTimeout"
),
OBSOLETE
(
"CloseHSServiceRendCircuitsImmediatelyOnTimeout"
),
V
(
HiddenServiceSingleHopMode
,
BOOL
,
"0"
),
...
...
@@ -1927,7 +1928,7 @@ options_act(const or_options_t *old_options)
// LCOV_EXCL_STOP
}
if
(
running_tor
&&
rend_parse_service_authorization
(
options
,
0
)
<
0
)
{
if
(
running_tor
&&
hs_config_client_auth_all
(
options
,
0
)
<
0
)
{
// LCOV_EXCL_START
log_warn
(
LD_BUG
,
"Previously validated client authorization for "
"hidden services could not be added!"
);
...
...
@@ -3193,6 +3194,8 @@ warn_about_relative_paths(or_options_t *options)
n
+=
warn_if_option_path_is_relative
(
"AccelDir"
,
options
->
AccelDir
);
n
+=
warn_if_option_path_is_relative
(
"DataDirectory"
,
options
->
DataDirectory
);
n
+=
warn_if_option_path_is_relative
(
"PidFile"
,
options
->
PidFile
);
n
+=
warn_if_option_path_is_relative
(
"ClientOnionAuthDir"
,
options
->
ClientOnionAuthDir
);
for
(
config_line_t
*
hs_line
=
options
->
RendConfigLines
;
hs_line
;
hs_line
=
hs_line
->
next
)
{
...
...
@@ -4344,7 +4347,7 @@ options_validate(or_options_t *old_options, or_options_t *options,
REJECT
(
"Failed to configure rendezvous options. See logs for details."
);
/* Parse client-side authorization for hidden services. */
if
(
rend_parse_service_authorization
(
options
,
1
)
<
0
)
if
(
hs_config_client_auth_all
(
options
,
1
)
<
0
)
REJECT
(
"Failed to configure client authorization for hidden services. "
"See logs for details."
);
...
...
src/app/config/or_options_st.h
View file @
9ca1af9a
...
...
@@ -380,6 +380,8 @@ struct or_options_t {
struct
config_line_t
*
HidServAuth
;
/**< List of configuration lines for
* client-side authorizations for hidden
* services */
char
*
ClientOnionAuthDir
;
/**< Directory to keep client
* onion service authorization secret keys */
char
*
ContactInfo
;
/**< Contact info to be published in the directory. */
int
HeartbeatPeriod
;
/**< Log heartbeat messages after this many seconds
...
...
src/feature/hs/hs_client.c
View file @
9ca1af9a
...
...
@@ -42,6 +42,10 @@
#include
"core/or/extend_info_st.h"
#include
"core/or/origin_circuit_st.h"
/* Client-side authorizations for hidden services; map of service identity
* public key to hs_client_service_authorization_t *. */
static
digest256map_t
*
client_auths
=
NULL
;
/* Return a human-readable string for the client fetch status code. */
static
const
char
*
fetch_status_to_string
(
hs_client_fetch_status_t
status
)
...
...
@@ -1177,6 +1181,19 @@ can_client_refetch_desc(const ed25519_public_key_t *identity_pk,
return
0
;
}
/* Return the client auth in the map using the service identity public key.
* Return NULL if it does not exist in the map. */
static
hs_client_service_authorization_t
*
find_client_auth
(
const
ed25519_public_key_t
*
service_identity_pk
)
{
/* If the map is not allocated, we can assume that we do not have any client
* auth information. */
if
(
!
client_auths
)
{
return
NULL
;
}
return
digest256map_get
(
client_auths
,
service_identity_pk
->
pubkey
);
}
/* ========== */
/* Public API */
/* ========== */
...
...
@@ -1215,11 +1232,19 @@ hs_client_decode_descriptor(const char *desc_str,
int
ret
;
uint8_t
subcredential
[
DIGEST256_LEN
];
ed25519_public_key_t
blinded_pubkey
;
hs_client_service_authorization_t
*
client_auth
=
NULL
;
curve25519_secret_key_t
*
client_auht_sk
=
NULL
;
tor_assert
(
desc_str
);
tor_assert
(
service_identity_pk
);
tor_assert
(
desc
);
/* Check if we have a client authorization for this service in the map. */
client_auth
=
find_client_auth
(
service_identity_pk
);
if
(
client_auth
)
{
client_auht_sk
=
&
client_auth
->
enc_seckey
;
}
/* Create subcredential for this HS so that we can decrypt */
{
uint64_t
current_time_period
=
hs_get_time_period_num
(
0
);
...
...
@@ -1229,7 +1254,8 @@ hs_client_decode_descriptor(const char *desc_str,
}
/* Parse descriptor */
ret
=
hs_desc_decode_descriptor
(
desc_str
,
subcredential
,
desc
);
ret
=
hs_desc_decode_descriptor
(
desc_str
,
subcredential
,
client_auht_sk
,
desc
);
memwipe
(
subcredential
,
0
,
sizeof
(
subcredential
));
if
(
ret
<
0
)
{
log_warn
(
LD_GENERAL
,
"Could not parse received descriptor as client."
);
...
...
@@ -1393,6 +1419,233 @@ hs_client_receive_rendezvous_acked(origin_circuit_t *circ,
return
-
1
;
}
#define client_service_authorization_free(auth) \
FREE_AND_NULL(hs_client_service_authorization_t, \
client_service_authorization_free_, (auth))
static
void
client_service_authorization_free_
(
hs_client_service_authorization_t
*
auth
)
{
if
(
auth
)
{
memwipe
(
auth
,
0
,
sizeof
(
*
auth
));
}
tor_free
(
auth
);
}
/** Helper for digest256map_free. */
static
void
client_service_authorization_free_void
(
void
*
auth
)
{
client_service_authorization_free_
(
auth
);
}
static
void
client_service_authorization_free_all
(
void
)
{
if
(
!
client_auths
)
{
return
;
}
digest256map_free
(
client_auths
,
client_service_authorization_free_void
);
}
/* Check if the auth key file name is valid or not. Return 1 if valid,
* otherwise return 0. */
STATIC
int
auth_key_filename_is_valid
(
const
char
*
filename
)
{
int
ret
=
1
;
const
char
*
valid_extension
=
".auth_private"
;
tor_assert
(
filename
);
/* The length of the filename must be greater than the length of the
* extension and the valid extension must be at the end of filename. */
if
(
!
strcmpend
(
filename
,
valid_extension
)
&&
strlen
(
filename
)
!=
strlen
(
valid_extension
))
{
ret
=
1
;
}
else
{
ret
=
0
;
}
return
ret
;
}
STATIC
hs_client_service_authorization_t
*
parse_auth_file_content
(
const
char
*
client_key_str
)
{
char
*
onion_address
=
NULL
;
char
*
auth_type
=
NULL
;
char
*
key_type
=
NULL
;
char
*
seckey_b32
=
NULL
;
hs_client_service_authorization_t
*
auth
=
NULL
;
smartlist_t
*
fields
=
smartlist_new
();
tor_assert
(
client_key_str
);
smartlist_split_string
(
fields
,
client_key_str
,
":"
,
SPLIT_SKIP_SPACE
,
0
);
/* Wrong number of fields. */
if
(
smartlist_len
(
fields
)
!=
4
)
{
goto
err
;
}
onion_address
=
smartlist_get
(
fields
,
0
);
auth_type
=
smartlist_get
(
fields
,
1
);
key_type
=
smartlist_get
(
fields
,
2
);
seckey_b32
=
smartlist_get
(
fields
,
3
);
/* Currently, the only supported auth type is "descriptor" and the only
* supported key type is "x25519". */
if
(
strcmp
(
auth_type
,
"descriptor"
)
||
strcmp
(
key_type
,
"x25519"
))
{
goto
err
;
}
if
(
strlen
(
seckey_b32
)
!=
BASE32_NOPAD_LEN
(
CURVE25519_PUBKEY_LEN
))
{
log_warn
(
LD_REND
,
"Client authorization encoded base32 private key "
"length is invalid: %s"
,
seckey_b32
);
goto
err
;
}
auth
=
tor_malloc_zero
(
sizeof
(
hs_client_service_authorization_t
));
if
(
base32_decode
((
char
*
)
auth
->
enc_seckey
.
secret_key
,
sizeof
(
auth
->
enc_seckey
.
secret_key
),
seckey_b32
,
strlen
(
seckey_b32
))
<
0
)
{
goto
err
;
}
strncpy
(
auth
->
onion_address
,
onion_address
,
HS_SERVICE_ADDR_LEN_BASE32
);
/* Success. */
goto
done
;
err:
client_service_authorization_free
(
auth
);
done:
/* It is also a good idea to wipe the private key. */
if
(
seckey_b32
)
{
memwipe
(
seckey_b32
,
0
,
strlen
(
seckey_b32
));
}
if
(
fields
)
{
SMARTLIST_FOREACH
(
fields
,
char
*
,
s
,
tor_free
(
s
));
smartlist_free
(
fields
);
}
return
auth
;
}
/* From a set of <b>options</b>, setup every client authorization detail
* found. Return 0 on success or -1 on failure. If <b>validate_only</b>
* is set, parse, warn and return as normal, but don't actually change
* the configuration. */
int
hs_config_client_authorization
(
const
or_options_t
*
options
,
int
validate_only
)
{
int
ret
=
-
1
;
digest256map_t
*
auths
=
digest256map_new
();
char
*
key_dir
=
NULL
;
smartlist_t
*
file_list
=
NULL
;
char
*
client_key_str
=
NULL
;
char
*
client_key_file_path
=
NULL
;
tor_assert
(
options
);
/* There is no client auth configured. We can just silently ignore this
* function. */
if
(
!
options
->
ClientOnionAuthDir
)
{
ret
=
0
;
goto
end
;
}
key_dir
=
tor_strdup
(
options
->
ClientOnionAuthDir
);
/* Make sure the directory exists and is private enough. */
if
(
check_private_dir
(
key_dir
,
0
,
options
->
User
)
<
0
)
{
goto
end
;
}
file_list
=
tor_listdir
(
key_dir
);
if
(
file_list
==
NULL
)
{
log_warn
(
LD_REND
,
"Client authorization key directory %s can't be listed."
,
key_dir
);
goto
end
;
}
SMARTLIST_FOREACH_BEGIN
(
file_list
,
char
*
,
filename
)
{
hs_client_service_authorization_t
*
auth
=
NULL
;
ed25519_public_key_t
identity_pk
;
log_info
(
LD_REND
,
"Loading a client authorization key file %s..."
,
filename
);
if
(
!
auth_key_filename_is_valid
(
filename
))
{
log_notice
(
LD_REND
,
"Client authorization unrecognized filename %s. "
"File must end in .auth_private. Ignoring."
,
filename
);
continue
;
}
/* Create a full path for a file. */
client_key_file_path
=
hs_path_from_filename
(
key_dir
,
filename
);
client_key_str
=
read_file_to_str
(
client_key_file_path
,
0
,
NULL
);
/* Free the file path immediately after using it. */
tor_free
(
client_key_file_path
);
/* If we cannot read the file, continue with the next file. */
if
(
!
client_key_str
)
{
log_warn
(
LD_REND
,
"The file %s cannot be read."
,
filename
);
continue
;
}
auth
=
parse_auth_file_content
(
client_key_str
);
/* Free immediately after using it. */
tor_free
(
client_key_str
);
if
(
auth
)
{
/* Parse the onion address to get an identity public key and use it
* as a key of global map in the future. */
if
(
hs_parse_address
(
auth
->
onion_address
,
&
identity_pk
,
NULL
,
NULL
)
<
0
)
{
client_service_authorization_free
(
auth
);
log_warn
(
LD_REND
,
"The onion address
\"
%s
\"
is invalid in "
"file %s"
,
filename
,
auth
->
onion_address
);
continue
;
}
if
(
digest256map_get
(
auths
,
identity_pk
.
pubkey
))
{
client_service_authorization_free
(
auth
);
log_warn
(
LD_REND
,
"Duplicate authorization for the same hidden "
"service address %s."
,
safe_str_client
(
auth
->
onion_address
));
goto
end
;
}
digest256map_set
(
auths
,
identity_pk
.
pubkey
,
auth
);
log_info
(
LD_REND
,
"Loaded a client authorization key file %s."
,
filename
);
}
}
SMARTLIST_FOREACH_END
(
filename
);
/* Success. */
ret
=
0
;
end:
tor_free
(
key_dir
);
tor_free
(
client_key_str
);
tor_free
(
client_key_file_path
);
if
(
file_list
)
{
SMARTLIST_FOREACH
(
file_list
,
char
*
,
s
,
tor_free
(
s
));
smartlist_free
(
file_list
);
}
if
(
!
validate_only
&&
ret
==
0
)
{
client_service_authorization_free_all
();
client_auths
=
auths
;
}
else
{
digest256map_free
(
auths
,
client_service_authorization_free_void
);
}
return
ret
;
}
/* This is called when a descriptor has arrived following a fetch request and
* has been stored in the client cache. Every entry connection that matches
* the service identity key in the ident will get attached to the hidden
...
...
@@ -1589,6 +1842,7 @@ hs_client_free_all(void)
{
/* Purge the hidden service request cache. */
hs_purge_last_hid_serv_requests
();
client_service_authorization_free_all
();
}
/* Purge all potentially remotely-detectable state held in the hidden
...
...
@@ -1621,3 +1875,13 @@ hs_client_dir_info_changed(void)
* AP_CONN_STATE_RENDDESC_WAIT state in order to fetch the descriptor. */
retry_all_socks_conn_waiting_for_desc
();
}
#ifdef TOR_UNIT_TESTS
STATIC
digest256map_t
*
get_hs_client_auths_map
(
void
)
{
return
client_auths
;
}
#endif
/* defined(TOR_UNIT_TESTS) */
src/feature/hs/hs_client.h
View file @
9ca1af9a
...
...
@@ -31,6 +31,16 @@ typedef enum {
HS_CLIENT_FETCH_PENDING
=
5
,
}
hs_client_fetch_status_t
;
/** Client-side configuration of authorization for a service. */
typedef
struct
hs_client_service_authorization_t
{
/* An curve25519 secret key used to compute decryption keys that
* allow the client to decrypt the hidden service descriptor. */
curve25519_secret_key_t
enc_seckey
;
/* An onion address that is used to connect to the onion service. */
char
onion_address
[
HS_SERVICE_ADDR_LEN_BASE32
+
1
];
}
hs_client_service_authorization_t
;
void
hs_client_note_connection_attempt_succeeded
(
const
edge_connection_t
*
conn
);
...
...
@@ -63,6 +73,9 @@ void hs_client_desc_has_arrived(const hs_ident_dir_conn_t *ident);
extend_info_t
*
hs_client_get_random_intro_from_edge
(
const
edge_connection_t
*
edge_conn
);
int
hs_config_client_authorization
(
const
or_options_t
*
options
,
int
validate_only
);
int
hs_client_reextend_intro_circuit
(
origin_circuit_t
*
circ
);
void
hs_client_purge_state
(
void
);
...
...
@@ -71,6 +84,11 @@ void hs_client_free_all(void);
#ifdef HS_CLIENT_PRIVATE
STATIC
int
auth_key_filename_is_valid
(
const
char
*
filename
);
STATIC
hs_client_service_authorization_t
*
parse_auth_file_content
(
const
char
*
client_key_str
);
STATIC
routerstatus_t
*
pick_hsdir_v3
(
const
ed25519_public_key_t
*
onion_identity_pk
);
...
...
@@ -86,6 +104,12 @@ STATIC int handle_rendezvous2(origin_circuit_t *circ, const uint8_t *payload,
MOCK_DECL
(
STATIC
hs_client_fetch_status_t
,
fetch_v3_desc
,
(
const
ed25519_public_key_t
*
onion_identity_pk
));
#ifdef TOR_UNIT_TESTS
STATIC
digest256map_t
*
get_hs_client_auths_map
(
void
);
#endif
/* defined(TOR_UNIT_TESTS) */
#endif
/* defined(HS_CLIENT_PRIVATE) */
#endif
/* !defined(TOR_HS_CLIENT_H) */
...
...
src/feature/hs/hs_config.c
View file @
9ca1af9a
...
...
@@ -27,7 +27,9 @@
#include
"feature/hs/hs_common.h"
#include
"feature/hs/hs_config.h"
#include
"feature/hs/hs_client.h"
#include
"feature/hs/hs_service.h"
#include
"feature/rend/rendclient.h"
#include
"feature/rend/rendservice.h"
#include
"lib/encoding/confline.h"
#include
"app/config/or_options_st.h"
...
...
@@ -613,3 +615,28 @@ hs_config_service_all(const or_options_t *options, int validate_only)
/* Tor main should call the free all function on error. */
return
ret
;
}
/* From a set of <b>options</b>, setup every client authorization found.
* Return 0 on success or -1 on failure. If <b>validate_only</b> is set,
* parse, warn and return as normal, but don't actually change the
* configured state. */
int
hs_config_client_auth_all
(
const
or_options_t
*
options
,
int
validate_only
)
{
int
ret
=
-
1
;
/* Configure v2 authorization. */
if
(
rend_parse_service_authorization
(
options
,
validate_only
)
<
0
)
{
goto
done
;
}
/* Configure v3 authorization. */
if
(
hs_config_client_authorization
(
options
,
validate_only
)
<
0
)
{
goto
done
;
}
/* Success. */
ret
=
0
;
done:
return
ret
;
}
src/feature/hs/hs_config.h
View file @
9ca1af9a
...
...
@@ -19,6 +19,7 @@
/* API */
int
hs_config_service_all
(
const
or_options_t
*
options
,
int
validate_only
);
int
hs_config_client_auth_all
(
const
or_options_t
*
options
,
int
validate_only
);
#endif
/* !defined(TOR_HS_CONFIG_H) */
src/feature/hs/hs_descriptor.c
View file @
9ca1af9a
This diff is collapsed.
Click to expand it.
src/feature/hs/hs_descriptor.h
View file @
9ca1af9a
...
...
@@ -37,12 +37,6 @@ struct link_specifier_t;
#define HS_DESC_CERT_LIFETIME (54 * 60 * 60)
/* Length of the salt needed for the encrypted section of a descriptor. */
#define HS_DESC_ENCRYPTED_SALT_LEN 16
/* Length of the secret input needed for the KDF construction which derives
* the encryption key for the encrypted data section of the descriptor. This
* adds up to 68 bytes being the blinded key, hashed subcredential and
* revision counter. */
#define HS_DESC_ENCRYPTED_SECRET_INPUT_LEN \
ED25519_PUBKEY_LEN + DIGEST256_LEN + sizeof(uint64_t)
/* Length of the KDF output value which is the length of the secret key,
* the secret IV and MAC key length which is the length of H() output. */
#define HS_DESC_ENCRYPTED_KDF_OUTPUT_LEN \
...
...
@@ -59,6 +53,17 @@ struct link_specifier_t;
#define HS_DESC_ENCRYPTED_KEY_LEN CIPHER256_KEY_LEN
#define HS_DESC_ENCRYPTED_BIT_SIZE (HS_DESC_ENCRYPTED_KEY_LEN * 8)
/* Length of each components in the auth client section in the descriptor. */
#define HS_DESC_CLIENT_ID_LEN 8
#define HS_DESC_DESCRIPTOR_COOKIE_LEN 16
#define HS_DESC_COOKIE_KEY_LEN 32
#define HS_DESC_COOKIE_KEY_BIT_SIZE (HS_DESC_COOKIE_KEY_LEN * 8)
#define HS_DESC_ENCRYPED_COOKIE_LEN HS_DESC_DESCRIPTOR_COOKIE_LEN
/* The number of auth client entries in the descriptor must be the multiple
* of this constant. */
#define HS_DESC_AUTH_CLIENT_MULTIPLE 16
/* Type of authentication in the descriptor. */
typedef
enum
{
HS_DESC_AUTH_ED25519
=
1
...
...
@@ -126,6 +131,20 @@ typedef struct hs_desc_intro_point_t {
unsigned
int
cross_certified
:
1
;
}
hs_desc_intro_point_t
;
/* Authorized client information located in a descriptor. */
typedef
struct
hs_desc_authorized_client_t
{
/* An identifier that the client will use to identify which auth client
* entry it needs to use. */
uint8_t
client_id
[
HS_DESC_CLIENT_ID_LEN
];
/* An IV that is used to decrypt the encrypted descriptor cookie. */
uint8_t
iv
[
CIPHER_IV_LEN
];
/* An encrypted descriptor cookie that the client needs to decrypt to use
* it to decrypt the descriptor. */
uint8_t
encrypted_cookie
[
HS_DESC_ENCRYPED_COOKIE_LEN
];
}
hs_desc_authorized_client_t
;
/* The encrypted data section of a descriptor. Obviously the data in this is
* in plaintext but encrypted once encoded. */
typedef
struct
hs_desc_encrypted_data_t
{
...
...
@@ -144,6 +163,24 @@ typedef struct hs_desc_encrypted_data_t {
smartlist_t
*
intro_points
;
}
hs_desc_encrypted_data_t
;
/* The superencrypted data section of a descriptor. Obviously the data in
* this is in plaintext but encrypted once encoded. */
typedef
struct
hs_desc_superencrypted_data_t
{
/* This field contains ephemeral x25519 public key which is used by
* the encryption scheme in the client authorization. */
curve25519_public_key_t
auth_ephemeral_pubkey
;
/* A list of authorized clients. Contains hs_desc_authorized_client_t
* objects. */
smartlist_t
*
clients
;
/* Decoding only: The b64-decoded encrypted blob from the descriptor */
uint8_t
*
encrypted_blob
;
/* Decoding only: Size of the encrypted_blob */
size_t
encrypted_blob_size
;
}
hs_desc_superencrypted_data_t
;
/* Plaintext data that is unencrypted information of the descriptor. */
typedef
struct
hs_desc_plaintext_data_t
{
/* Version of the descriptor format. Spec specifies this field as a
...
...
@@ -182,6 +219,11 @@ typedef struct hs_descriptor_t {
/* Contains the plaintext part of the descriptor. */
hs_desc_plaintext_data_t
plaintext_data
;
/* The following contains what's in the superencrypted part of the
* descriptor. It's only encrypted in the encoded version of the descriptor
* thus the data contained in that object is in plaintext. */
hs_desc_superencrypted_data_t
superencrypted_data
;
/* The following contains what's in the encrypted part of the descriptor.
* It's only encrypted in the encoded version of the descriptor thus the
* data contained in that object is in plaintext. */
...
...
@@ -211,6 +253,10 @@ void hs_descriptor_free_(hs_descriptor_t *desc);
void
hs_desc_plaintext_data_free_
(
hs_desc_plaintext_data_t
*
desc
);
#define hs_desc_plaintext_data_free(desc) \
FREE_AND_NULL(hs_desc_plaintext_data_t, hs_desc_plaintext_data_free_, (desc))
void
hs_desc_superencrypted_data_free_
(
hs_desc_superencrypted_data_t
*
desc
);
#define hs_desc_superencrypted_data_free(desc) \
FREE_AND_NULL(hs_desc_superencrypted_data_t, \
hs_desc_superencrypted_data_free_, (desc))
void
hs_desc_encrypted_data_free_
(
hs_desc_encrypted_data_t
*
desc
);
#define hs_desc_encrypted_data_free(desc) \
FREE_AND_NULL(hs_desc_encrypted_data_t, hs_desc_encrypted_data_free_, (desc))
...
...
@@ -226,14 +272,19 @@ void hs_descriptor_clear_intro_points(hs_descriptor_t *desc);
MOCK_DECL
(
int
,
hs_desc_encode_descriptor
,(
const
hs_descriptor_t
*
desc
,
const
ed25519_keypair_t
*
signing_kp
,
const
uint8_t
*
descriptor_cookie
,
char
**
encoded_out
));
int
hs_desc_decode_descriptor
(
const
char
*
encoded
,
const
uint8_t
*
subcredential
,
const
curve25519_secret_key_t
*
client_auth_sk
,
hs_descriptor_t
**
desc_out
);
int
hs_desc_decode_plaintext
(
const
char
*
encoded
,
hs_desc_plaintext_data_t
*
plaintext
);
int
hs_desc_decode_superencrypted
(
const
hs_descriptor_t
*
desc
,
hs_desc_superencrypted_data_t
*
desc_out
);
int
hs_desc_decode_encrypted
(
const
hs_descriptor_t
*
desc
,
const
curve25519_secret_key_t
*
client_auth_sk
,
hs_desc_encrypted_data_t
*
desc_out
);
size_t
hs_desc_obj_size
(
const
hs_descriptor_t
*
data
);
...
...
@@ -243,10 +294,27 @@ hs_desc_intro_point_t *hs_desc_intro_point_new(void);
void
hs_desc_intro_point_free_
(
hs_desc_intro_point_t
*
ip
);
#define hs_desc_intro_point_free(ip) \
FREE_AND_NULL(hs_desc_intro_point_t, hs_desc_intro_point_free_, (ip))
void
hs_desc_authorized_client_free_
(
hs_desc_authorized_client_t
*
client
);
#define hs_desc_authorized_client_free(client) \
FREE_AND_NULL(hs_desc_authorized_client_t, \
hs_desc_authorized_client_free_, (client))
link_specifier_t
*
hs_desc_lspec_to_trunnel
(
const
hs_desc_link_specifier_t
*
spec
);
hs_desc_authorized_client_t
*
hs_desc_build_fake_authorized_client
(
void
);
void
hs_desc_build_authorized_client
(
const
uint8_t
*
subcredential
,
const
curve25519_public_key_t
*
client_auth_pk
,
const
curve25519_secret_key_t
*
auth_ephemeral_sk
,
const
uint8_t
*
descriptor_cookie
,
hs_desc_authorized_client_t
*
client_out
);
void
hs_desc_plaintext_data_free_contents
(
hs_desc_plaintext_data_t
*
desc
);
void
hs_desc_superencrypted_data_free_contents
(
hs_desc_superencrypted_data_t
*
desc
);
void
hs_desc_encrypted_data_free_contents
(
hs_desc_encrypted_data_t
*
desc
);
#ifdef HS_DESCRIPTOR_PRIVATE
/* Encoding. */
...
...
@@ -265,13 +333,11 @@ STATIC int cert_is_valid(tor_cert_t *cert, uint8_t type,
STATIC
int
desc_sig_is_valid
(
const
char
*
b64_sig
,
const
ed25519_public_key_t
*
signing_pubkey
,
const
char
*
encoded_desc
,
size_t
encoded_len
);
STATIC
size_t
decode_superencrypted
(
const
char
*
message
,
size_t
message_len
,
uint8_t
**
encrypted_out
);
STATIC
void
desc_plaintext_data_free_contents
(
hs_desc_plaintext_data_t
*
desc
);
MOCK_DECL
(
STATIC
size_t
,
decrypt_desc_layer
,(
const
hs_descriptor_t
*
desc
,
const
uint8_t
*
encrypted_blob
,
size_t
encrypted_blob_size
,
const
uint8_t
*
descriptor_cookie
,
int
is_superencrypted_layer
,
char
**
decrypted_out
));
...
...
src/feature/hs/hs_service.c
View file @
9ca1af9a
This diff is collapsed.
Click to expand it.
src/feature/hs/hs_service.h
View file @
9ca1af9a
...
...
@@ -105,6 +105,13 @@ typedef struct hs_service_descriptor_t {
* publishes the descriptor. */