Skip to content

Commit d1eac4b

Browse files
authored
Advance resource management (#320)
Decopule the lifetime of msquic handle and nif resource context. The resource in msquic could be released earlier before the deallocation of erlang NIF resource with some cost of extra refcnts overheads. Benefits: For correctness, do not rely on the internal ref countings in MsQuic, take it as black box. Further reduce memory footprints at server side, adapt to more dynamic environments. simplify the logic of resource management at both msquic side and erlang nif side. make it more flexible to operate the stack, support more dynamic configuration.
1 parent 6275a79 commit d1eac4b

29 files changed

+1044
-732
lines changed

Diff for: .github/workflows/hex_pub.yml

+1-1
Original file line numberDiff line numberDiff line change
@@ -4,8 +4,8 @@ on:
44
- '*'
55

66
jobs:
7-
if: false
87
publish:
8+
if: false
99
runs-on: ubuntu-latest
1010
steps:
1111
- name: Check out

Diff for: .github/workflows/main.yml

+36-4
Original file line numberDiff line numberDiff line change
@@ -21,9 +21,41 @@ jobs:
2121
run: |
2222
rebar3 fmt -c
2323
24-
mac:
25-
timeout-minutes: 60
24+
pre-check:
25+
name: Pre check
2626
needs: formatting-check
27+
runs-on: ubuntu-latest
28+
timeout-minutes: 25
29+
strategy:
30+
fail-fast: false
31+
matrix:
32+
# https://builds.hex.pm/builds/otp/ubuntu-22.04/builds.txt
33+
otp:
34+
- 26.2.5.3
35+
rebar3:
36+
- 3.23.0
37+
steps:
38+
- name: Checkout
39+
uses: actions/checkout@a5ac7e51b41094c92402da3b24376905380afc29 # v4.1.6
40+
with:
41+
submodules: recursive
42+
- uses: erlef/setup-beam@2f0cc07b4b9bea248ae098aba9e1a8a1de5ec24c # v1.17.5
43+
with:
44+
otp-version: ${{ matrix.otp }}
45+
rebar3-version: ${{ matrix.rebar3 }}
46+
- name: release build with debug log off
47+
run: |
48+
echo "github ref: ${{ github.event.ref }}"
49+
echo "github ref: ${{ github.ref }}"
50+
sudo sysctl -w kernel.core_pattern=core
51+
ulimit -c unlimited
52+
export CMAKE_BUILD_TYPE=Debug
53+
export QUICER_TLS_VER=sys
54+
make ci
55+
56+
mac-mesh:
57+
timeout-minutes: 60
58+
needs: pre-check
2759
strategy:
2860
fail-fast: false
2961
matrix:
@@ -78,8 +110,8 @@ jobs:
78110
retention-days: 1
79111

80112

81-
linux:
82-
needs: formatting-check
113+
linux-mesh:
114+
needs: pre-check
83115
runs-on: ubuntu-latest
84116
timeout-minutes: 25
85117
strategy:

Diff for: c_src/quicer_config.c

+19-30
Original file line numberDiff line numberDiff line change
@@ -20,7 +20,7 @@ limitations under the License.
2020
#include "quicer_tls.h"
2121
#include <msquichelper.h>
2222

23-
extern QuicerRegistrationCTX *G_r_ctx;
23+
extern QuicerRegistrationCTX G_r_ctx;
2424
extern pthread_mutex_t MsQuicLock;
2525

2626
static ERL_NIF_TERM get_stream_opt(ErlNifEnv *env,
@@ -218,11 +218,6 @@ ServerLoadConfiguration(ErlNifEnv *env,
218218
{
219219
QUIC_SETTINGS Settings = { 0 };
220220

221-
if (!G_r_ctx)
222-
{
223-
return ATOM_REG_FAILED;
224-
}
225-
226221
if (!create_settings(env, option, &Settings))
227222
{
228223
return ATOM_BADARG;
@@ -275,11 +270,6 @@ ClientLoadConfiguration(ErlNifEnv *env,
275270
QUIC_SETTINGS Settings = { 0 };
276271
ERL_NIF_TERM ret = ATOM_OK;
277272

278-
if (!G_r_ctx)
279-
{
280-
return ATOM_REG_FAILED;
281-
}
282-
283273
//
284274
// Configures the client's idle timeout.
285275
//
@@ -859,10 +849,9 @@ encode_parm_to_eterm(ErlNifEnv *env,
859849
}
860850

861851
ERL_NIF_TERM
862-
getopt3(ErlNifEnv *env,
863-
__unused_parm__ int argc,
864-
__unused_parm__ const ERL_NIF_TERM argv[])
852+
getopt3(ErlNifEnv *env, int argc, const ERL_NIF_TERM argv[])
865853
{
854+
CXPLAT_FRE_ASSERT(3 == argc);
866855
ERL_NIF_TERM ctx = argv[0];
867856
ERL_NIF_TERM eopt = argv[1];
868857
ERL_NIF_TERM elevel = argv[2];
@@ -894,12 +883,12 @@ getopt3(ErlNifEnv *env,
894883
{
895884
return SUCCESS(ETERM_UINT_64(((QuicerStreamCTX *)q_ctx)->StreamID));
896885
}
897-
if (!get_stream_handle(q_ctx))
886+
if (!LOCAL_REFCNT(get_stream_handle(q_ctx)))
898887
{
899888
goto Exit;
900889
}
901890
res = get_stream_opt(env, (QuicerStreamCTX *)q_ctx, eopt, elevel);
902-
put_stream_handle(q_ctx);
891+
LOCAL_REFCNT(put_stream_handle(q_ctx));
903892
}
904893
else if (enif_get_resource(env, ctx, ctx_connection_t, &q_ctx))
905894
{
@@ -971,8 +960,9 @@ set_level_param(ErlNifEnv *env,
971960
}
972961

973962
ERL_NIF_TERM
974-
setopt4(ErlNifEnv *env, __unused_parm__ int argc, const ERL_NIF_TERM argv[])
963+
setopt4(ErlNifEnv *env, int argc, const ERL_NIF_TERM argv[])
975964
{
965+
CXPLAT_FRE_ASSERT(4 == argc);
976966
ERL_NIF_TERM ctx = argv[0];
977967
ERL_NIF_TERM eopt = argv[1];
978968
ERL_NIF_TERM evalue = argv[2];
@@ -992,13 +982,13 @@ setopt4(ErlNifEnv *env, __unused_parm__ int argc, const ERL_NIF_TERM argv[])
992982
}
993983
else if (enif_get_resource(env, ctx, ctx_stream_t, &q_ctx))
994984
{
995-
if (!get_stream_handle(q_ctx))
985+
if (!LOCAL_REFCNT(get_stream_handle(q_ctx)))
996986
{
997987
goto Exit;
998988
}
999989
res = set_stream_opt(
1000990
env, (QuicerStreamCTX *)q_ctx, eopt, evalue, elevel);
1001-
put_stream_handle(q_ctx);
991+
LOCAL_REFCNT(put_stream_handle(q_ctx));
1002992
}
1003993
else if (enif_get_resource(env, ctx, ctx_connection_t, &q_ctx))
1004994
{
@@ -1344,7 +1334,7 @@ get_stream_opt(ErlNifEnv *env,
13441334
{
13451335
res = get_level_param(env,
13461336
s_ctx->Stream,
1347-
s_ctx->c_ctx->config_resource->Configuration,
1337+
s_ctx->c_ctx->config_ctx->Configuration,
13481338
optname,
13491339
elevel);
13501340
goto Exit;
@@ -1458,7 +1448,7 @@ set_stream_opt(ErlNifEnv *env,
14581448
{
14591449
res = set_level_param(env,
14601450
s_ctx->Stream,
1461-
s_ctx->c_ctx->config_resource->Configuration,
1451+
s_ctx->c_ctx->config_ctx->Configuration,
14621452
optname,
14631453
optval,
14641454
elevel);
@@ -1531,13 +1521,13 @@ get_connection_opt(ErlNifEnv *env,
15311521

15321522
if (!IS_SAME_TERM(ATOM_FALSE, elevel))
15331523
{
1534-
if (!c_ctx->config_resource)
1524+
if (!c_ctx->config_ctx)
15351525
{
15361526
goto Exit;
15371527
}
15381528
res = get_level_param(env,
15391529
c_ctx->Connection,
1540-
c_ctx->config_resource->Configuration,
1530+
c_ctx->config_ctx->Configuration,
15411531
optname,
15421532
elevel);
15431533
goto Exit;
@@ -1724,13 +1714,13 @@ set_connection_opt(ErlNifEnv *env,
17241714

17251715
if (!IS_SAME_TERM(ATOM_FALSE, elevel))
17261716
{
1727-
if (!c_ctx->config_resource)
1717+
if (!c_ctx->config_ctx)
17281718
{
17291719
goto Exit;
17301720
}
17311721
res = set_level_param(env,
17321722
c_ctx->Connection,
1733-
c_ctx->config_resource->Configuration,
1723+
c_ctx->config_ctx->Configuration,
17341724
optname,
17351725
optval,
17361726
elevel);
@@ -2062,13 +2052,13 @@ get_listener_opt(ErlNifEnv *env,
20622052
{
20632053
return ERROR_TUPLE_2(ATOM_CLOSED);
20642054
}
2065-
enif_keep_resource(l_ctx);
2055+
get_listener_handle(l_ctx);
20662056

20672057
if (!IS_SAME_TERM(ATOM_FALSE, elevel))
20682058
{
20692059
res = get_level_param(env,
20702060
l_ctx->Listener,
2071-
l_ctx->config_resource->Configuration,
2061+
l_ctx->config_ctx->Configuration,
20722062
optname,
20732063
elevel);
20742064
goto Exit;
@@ -2123,7 +2113,7 @@ get_listener_opt(ErlNifEnv *env,
21232113
res = ERROR_TUPLE_2(ATOM_STATUS(status));
21242114
}
21252115
Exit:
2126-
enif_release_resource(l_ctx);
2116+
put_listener_handle(l_ctx);
21272117
return res;
21282118
}
21292119

@@ -2157,7 +2147,7 @@ set_listener_opt(ErlNifEnv *env,
21572147
{
21582148
res = set_level_param(env,
21592149
l_ctx->Listener,
2160-
l_ctx->config_resource->Configuration,
2150+
l_ctx->config_ctx->Configuration,
21612151
optname,
21622152
optval,
21632153
elevel);
@@ -2644,7 +2634,6 @@ parse_registration(ErlNifEnv *env,
26442634
return FALSE;
26452635
}
26462636
}
2647-
26482637
return TRUE;
26492638
}
26502639

0 commit comments

Comments
 (0)