Add HiddenServiceExportRendPoint and HiddenServiceExportInstanceID directive to export rendezvous point information and instance ID along with circuit ID
Trac: Username: moonsikpark
To upload designs, you'll need to enable LFS and have an admin enable hashed storage. More information
Child items 0
Show closed items
No child items are currently assigned. Use child items to break down this issue into smaller parts.
Linked items 0
Link issues together to show that they're related.
Learn more.
I left some comments there. I think my biggest question is what is the IPv6 story in this? Encoding a 32-bit IPv4 address in an IPv6 address is smart, but encoding an IPv6 address in an IPv6 address whilst still leaving space for other data is going to be difficult.
I left some comments there. I think my biggest question is what is the IPv6 story in this? Encoding a 32-bit IPv4 address in an IPv6 address is smart, but encoding an IPv6 address in an IPv6 address whilst still leaving space for other data is going to be difficult.
The PROXY protocol has 2 address fields and 2 port fields:
PROXY TCP6 (SOURCE_IPV6) (DEST_IPV6) (SOURCE_PORT) (DEST_PORT)
In the current Tor network, Tor relays must have one IPv4 address and port, and can optionally have an IPv6 address and port.
So here's the information we might want to capture:
REND_IPV4 (4 bytes)
REND_IPV4_PORT (2 bytes)
REND_IPV6 (16 bytes)
REND_IPV6_PORT (2 bytes)
INSTANCE_ID (2 bytes)
CIRCUIT_ID (4 bytes)
And here's how this patch does that:
PROXY TCP6 (RESERVED_4_BYTES|REND_IPV4|REND_IPV4_PORT|INSTANCE_ID|CIRCUIT_ID) (::1) (1) (0)
If we ever need to capture the IPv6 address and port:
If we can use DEST_IPV6 and DEST_PORT:
Use DEST_IPV6 for REND_IPV6
Use DEST_PORT for REND_IPV6_PORT
If we can't, we only have 4 bytes left to store 18 bytes, so we hash the IPv6 and port, and use the first 4 bytes:
But we should definitely document that IPv6 is not supported, and that the address is the canonical IPv4 address of the rend point. (And not guaranteed to be the actual address that the circuit is connecting through.)
Actually, we can't use RESERVED_4_BYTES, because it's set to "fc00". We'd have to use one of the other fields instead. (Or replace the IPv4 address with the hash.)
2697bash.exe : In file included from ../src/test/test_hs_service.c:38:2698At line:2 char:52699+ & $commandPath $args 2>&12700+ ~~~~~~~~~~~~~~~~~~~~~~~~~2701 + CategoryInfo : NotSpecified: (In file include...s_service.c:38::String) [], RemoteException2702 + FullyQualifiedErrorId : NativeCommandError2703 2704../src/test/test_hs_service.c: In function 'test_export_client_circuit_id':27052706../src/core/or/circuitbuild.h:61:32: error: 'chosen_exit' may be used uninitialized in this function [-Werror=maybe-uninitialized]2707 61 | FREE_AND_NULL(extend_info_t, extend_info_free_, (info))2708 | ^~~~~~~~~~~~~~~~~27092710../src/test/test_hs_service.c:2209:18: note: 'chosen_exit' was declared here2711 2209 | extend_info_t *chosen_exit = NULL;2712 | ^~~~~~~~~~~27132714cc1.exe: all warnings being treated as errors27152716make[1]: *** [Makefile:19844: src/test/test-test_hs_service.o] Error 127172718
5505hs_service/export_client_circuit_id: [forking] =================================================================5506==36432==ERROR: AddressSanitizer: heap-use-after-free on address 0x60e000107338 at pc 0x000100781651 bp 0x7ffeef985f60 sp 0x7ffeef985f585507READ of size 8 at 0x60e000107338 thread T05508 #0 0x100781650 in extend_info_free_ circuitbuild.c:27985509 #1 0x10078c55e in circuit_free_ circuitlist.c:11595510 #2 0x1004fd8e5 in test_export_client_circuit_id test_hs_service.c:22885511 #3 0x1006f39b3 in testcase_run_one tinytest.c:1075512 #4 0x1006f4282 in tinytest_main tinytest.c:4545513 #5 0x1006f1ec7 in main testing_common.c:3505514 #6 0x7fff7964e3d4 in start (libdyld.dylib:x86_64+0x163d4)551555160x60e000107338 is located 120 bytes inside of 160-byte region [0x60e0001072c0,0x60e000107360)5517freed by thread T0 here:5518 #0 0x101d53bad in wrap_free (libclang_rt.asan_osx_dynamic.dylib:x86_64+0x5ebad)5519 #1 0x1004fd8bb in test_export_client_circuit_id test_hs_service.c:22865520 #2 0x1006f39b3 in testcase_run_one tinytest.c:1075521 #3 0x1006f4282 in tinytest_main tinytest.c:4545522 #4 0x1006f1ec7 in main testing_common.c:3505523 #5 0x7fff7964e3d4 in start (libdyld.dylib:x86_64+0x163d4)55245525previously allocated by thread T0 here:5526 #0 0x101d539f3 in wrap_malloc (libclang_rt.asan_osx_dynamic.dylib:x86_64+0x5e9f3)5527 #1 0x100ad6bef in tor_malloc_zero_ malloc.c:455528 #2 0x100782e3d in extend_info_new circuitbuild.c:26905529 #3 0x1004fe98c in test_export_client_circuit_id test_hs_service.c:22725530 #4 0x1006f39b3 in testcase_run_one tinytest.c:1075531 #5 0x1006f4282 in tinytest_main tinytest.c:4545532 #6 0x1006f1ec7 in main testing_common.c:3505533 #7 0x7fff7964e3d4 in start (libdyld.dylib:x86_64+0x163d4)
OK, made CI happy by letting circuit_free_() free or_circ->build_state->chosen_exit.
Before extending the exposure range of rp fingerprint, I think there might be other metrics we can export that can help onion services. Potentially circ->rend_data->nr_streams or circ->hs_ident->intro_auth_pk or circ->hs_ident->rendezvous_cookie. If we can't export all 20 bytes, exporting part of it and exporting other things like which intro point did the client choose? or what was the rendezvous cookie? or how many streams is the client opening now? might help.
I think INSTANCE_ID don't have to be that long, we can change it to 1 byte and move it to the front(fdAA where AA=INSTANCE_ID).
And I'm curious about dst_ipv6 fixed to ::1. real_addr of rend_service_port_config_t is not always localhost. Does backends ignore the destination address? Does it mean we can cram data in dst_ipv6 too?
OK, made CI happy by letting circuit_free_() free or_circ->build_state->chosen_exit.
Thanks!
Before extending the exposure range of rp fingerprint, I think there might be other metrics we can export that can help onion services. Potentially circ->rend_data->nr_streams or circ->hs_ident->intro_auth_pk
Sure that seems fine.
or circ->hs_ident->rendezvous_cookie.
No, I don't think we should export raw cryptographic material. If you really want this info, you should export siphash(circ->hs_ident->rendezvous_cookie). (The cookie should not be common across instances, unless the client is doing a replay attack across different instances. If you want to be able to detect relay attacks, you should do H(CONSTANT_PREFIX|circ->hs_ident->rendezvous_cookie).)
I think INSTANCE_ID don't have to be that long, we can change it to 1 byte and move it to the front(fdAA where AA=INSTANCE_ID).
Sure.
And I'm curious about dst_ipv6 fixed to ::1. real_addr of rend_service_port_config_t is not always localhost. Does backends ignore the destination address?
I don't know who is actually using this feature right now. Maybe ahf does?
Does it mean we can cram data in dst_ipv6 too?
That's 16 bytes, so you could get the whole fingerprint if you wanted it. But maybe there are more valuable things.
No, I don't think we should export raw cryptographic material. If you really want this info, you should export siphash(circ->hs_ident->rendezvous_cookie). (The cookie should not be common across instances, unless the client is doing a replay attack across different instances. If you want to be able to detect relay attacks, you should do H(CONSTANT_PREFIX|circ->hs_ident->rendezvous_cookie).)
I agree. Should we have a new variable that stores H(CONSTANT_PREFIX|circ->hs_ident->rendezvous_cookie) in rend_data_t?
I'm going to suggest a way forward:
We land this patch with the current fields, in the positions they will have in the final design.
We open a new ticket for any new fields.
This feature is getting complex enough that we might need a proposal, a spec, or a very well-designed manual page entry.
Edit: I agree. Let's get this over with first.
I think writing a proposal or a spec is the way to go considering the complexity. How do I write a proposal or a spec?