4 #include "vg/vg_stdint.h"
6 #include "network_msg.h"
7 #include "highscores.h"
12 #define SR_USE_LOCALHOST
14 /* Call it at start; Connects us to the gameserver */
15 static void network_init(void);
17 /* Run this from main loop */
18 static void network_update(void);
20 /* Call it at shutdown */
21 static void network_end(void);
24 * Can buffer up a bunch of these by calling many times, they will be
25 * sent at the next connection
27 static void network_submit_highscore( u32 trackid
, u16 points
, u16 time
);
30 * Game endpoints are provided with the same names to allow running without a
36 * Runtime connection stuff
38 static u8 steam_app_ticket
[ 1024 ];
39 static u32 steam_app_ticket_length
;
40 static int network_name_update
= 1;
42 static HSteamNetConnection cremote
;
43 static ESteamNetworkingConnectionState cremote_state
=
44 k_ESteamNetworkingConnectionState_None
;
50 static void scores_update(void);
52 static void on_auth_ticket_recieved( void *result
, void *context
)
54 EncryptedAppTicketResponse_t
*response
= result
;
56 if( response
->m_eResult
== k_EResultOK
)
58 vg_info( " New app ticket ready\n" );
62 vg_warn( " Could not request new encrypted app ticket (%u)\n",
63 response
->m_eResult
);
66 if( SteamAPI_ISteamUser_GetEncryptedAppTicket( hSteamUser
,
68 vg_list_size(steam_app_ticket
),
69 &steam_app_ticket_length
))
71 vg_success( " Loaded app ticket (%u bytes)\n", steam_app_ticket_length
);
75 vg_error( " No ticket availible\n" );
76 steam_app_ticket_length
= 0;
80 static void request_auth_ticket(void)
83 * TODO Check for one thats cached on the disk and load it.
84 * This might be OK though because steam seems to cache the result
87 vg_info( "Requesting new authorization ticket\n" );
88 steam_async
*call
= steam_new_async();
90 call
->p_handler
= on_auth_ticket_recieved
;
91 call
->id
= SteamAPI_ISteamUser_RequestEncryptedAppTicket( hSteamUser
,
95 static void send_auth_ticket(void)
97 u32 size
= sizeof(netmsg_auth
) + steam_app_ticket_length
;
98 netmsg_auth
*auth
= alloca(size
);
100 auth
->inetmsg_id
= k_inetmsg_auth
;
101 auth
->ticket_length
= steam_app_ticket_length
;
102 for( int i
=0; i
<steam_app_ticket_length
; i
++ )
103 auth
->ticket
[i
] = steam_app_ticket
[i
];
105 SteamAPI_ISteamNetworkingSockets_SendMessageToConnection(
106 hSteamNetworkingSockets
, cremote
, auth
, size
,
107 k_nSteamNetworkingSend_Reliable
, NULL
);
110 static void send_score_request(void)
112 vg_info( "Requesting scores\n" );
113 netmsg_scores_request req
;
114 req
.inetmsg_id
= k_inetmsg_scores_request
;
116 SteamAPI_ISteamNetworkingSockets_SendMessageToConnection(
117 hSteamNetworkingSockets
, cremote
, &req
, sizeof(netmsg_scores_request
),
118 k_nSteamNetworkingSend_Reliable
, NULL
);
121 static void send_score_update(void)
123 vg_info( "Sending scores\n" );
124 u32 size
= sizeof(netmsg_set_score
) +
125 1 * sizeof(struct netmsg_score_record
);
127 netmsg_set_score
*setscore
= alloca( size
);
128 setscore
->inetmsg_id
= k_inetmsg_set_score
;
129 setscore
->record_count
= 1;
130 setscore
->records
[0].trackid
= 0;
131 setscore
->records
[0].playerid
= 0;
132 setscore
->records
[0].points
= 1386;
133 setscore
->records
[0].time
= 19432;
135 SteamAPI_ISteamNetworkingSockets_SendMessageToConnection(
136 hSteamNetworkingSockets
, cremote
, setscore
, size
,
137 k_nSteamNetworkingSend_Reliable
, NULL
);
140 static void send_nickname(void)
142 netmsg_set_nickname nick
;
143 nick
.inetmsg_id
= k_inetmsg_set_nickname
;
145 memset( nick
.nickname
, 0, 10 );
146 strcpy( nick
.nickname
, "real H" );
148 SteamAPI_ISteamNetworkingSockets_SendMessageToConnection(
149 hSteamNetworkingSockets
, cremote
, &nick
, sizeof(netmsg_set_nickname
),
150 k_nSteamNetworkingSend_Reliable
, NULL
);
152 network_name_update
= 0;
155 static void server_routine_update(void)
159 if( network_name_update
)
163 send_score_request();
166 static void on_server_connect_status( CallbackMsg_t
*msg
)
168 SteamNetConnectionStatusChangedCallback_t
*info
= (void *)msg
->m_pubParam
;
169 vg_info( " Connection status changed for %lu\n", info
->m_hConn
);
170 vg_info( " %s -> %s\n",
171 string_ESteamNetworkingConnectionState(info
->m_eOldState
),
172 string_ESteamNetworkingConnectionState(info
->m_info
.m_eState
) );
174 if( info
->m_hConn
== cremote
)
176 cremote_state
= info
->m_info
.m_eState
;
177 if( info
->m_info
.m_eState
==
178 k_ESteamNetworkingConnectionState_Connected
)
180 vg_success(" Connected to remote server.. running updates\n");
181 server_routine_update();
186 vg_warn( " Recieved signal from unknown connection\n" );
190 static void network_connect_gc(void)
192 /* Connect to server if not connected */
193 SteamNetworkingIPAddr remoteAddr
;
195 #ifdef SR_USE_LOCALHOST
196 SteamAPI_SteamNetworkingIPAddr_SetIPv6LocalHost( &remoteAddr
, 27402 );
198 const char *server_lon1
= "46.101.34.155:27402";
199 SteamAPI_SteamNetworkingIPAddr_ParseString( &remoteAddr
, server_lon1
);
203 SteamAPI_SteamNetworkingIPAddr_ToString( &remoteAddr
, buf
, 256, 1 );
204 vg_info( "connect to: %s\n", buf
);
206 cremote
= SteamAPI_ISteamNetworkingSockets_ConnectByIPAddress(
207 hSteamNetworkingSockets
, &remoteAddr
, 0, NULL
);
210 static void on_inet_scoreboard( SteamNetworkingMessage_t
*msg
)
212 netmsg_scoreboard
*sb
= msg
->m_pData
;
214 u32 base_size
= sizeof(netmsg_scoreboard
)-
215 sizeof(struct netmsg_board
)*vg_list_size(track_infos
),
216 expected
= base_size
+sizeof(struct netmsg_board
)*sb
->board_count
;
218 if( msg
->m_cbSize
!= expected
)
220 vg_error( "Server scoreboard was corrupted. Size: %u != %u\n",
221 msg
->m_cbSize
, expected
);
225 if( vg_list_size(track_infos
) > sb
->board_count
)
226 vg_warn( "Server is out of date, not enough boards recieved\n");
227 else if( vg_list_size(track_infos
) < sb
->board_count
)
228 vg_warn( "Client out of date, server sent more boards than we have\n");
230 vg_success( "Recieved new scoreboards from server\n" );
232 for( int i
=0; i
< vg_min(sb
->board_count
,vg_list_size(track_infos
)); i
++)
234 scoreboard_client_data
.boards
[i
] = sb
->boards
[i
];
235 highscores_board_printf( stdout
, sb
->boards
[i
].data
, 10 );
239 /* We dont need to stay on the server currently */
240 SteamAPI_ISteamNetworkingSockets_CloseConnection(
241 hSteamNetworkingSockets
, cremote
, 0, NULL
, 1 );
244 static void poll_connection(void)
246 SteamNetworkingMessage_t
*messages
[32];
251 len
= SteamAPI_ISteamNetworkingSockets_ReceiveMessagesOnConnection(
252 hSteamNetworkingSockets
, cremote
, messages
, vg_list_size(messages
));
257 for( int i
=0; i
<len
; i
++ )
259 SteamNetworkingMessage_t
*msg
= messages
[i
];
261 if( msg
->m_cbSize
< sizeof(netmsg_blank
) )
263 vg_warn( "Discarding message (too small: %d)\n", msg
->m_cbSize
);
267 netmsg_blank
*tmp
= msg
->m_pData
;
269 if( tmp
->inetmsg_id
== k_inetmsg_scoreboard
)
270 on_inet_scoreboard( msg
);
272 SteamAPI_SteamNetworkingMessage_t_Release( msg
);
278 * Subroutine to be connected to main game loop, runs all routines on timers
280 static void network_update(void)
284 static double last_update
= 0.0;
287 if( vg_time
> (last_update
+ 60.0) )
289 last_update
= vg_time
;
291 if( steam_app_ticket_length
)
293 network_connect_gc();
297 vg_log( "Not making remote connection; app ticket not gotten\n" );
301 if( vg_time
> (last_update
+ 10.0) &&
302 (cremote_state
== k_ESteamNetworkingConnectionState_Connected
))
304 vg_warn( "Connected to server but no return... disconnecting\n" );
305 SteamAPI_ISteamNetworkingSockets_CloseConnection(
306 hSteamNetworkingSockets
, cremote
, 0, NULL
, 1 );
311 static void network_init(void)
315 steam_register_callback( k_iSteamNetConnectionStatusChangedCallBack
,
316 on_server_connect_status
);
317 request_auth_ticket();
321 static void network_end(void)
323 /* TODO: Fire off any buffered highscores that need to be setn */
324 if( cremote_state
== k_ESteamNetworkingConnectionState_Connected
||
325 cremote_state
== k_ESteamNetworkingConnectionState_Connecting
)
327 SteamAPI_ISteamNetworkingSockets_CloseConnection(
328 hSteamNetworkingSockets
, cremote
, 0, NULL
, 1 );
332 #else /* SR_NETWORKED */
334 static void network_init(void){}
335 static void network_update(void){}
336 static void network_end(void){}
338 #endif /* SR_NETWORKED */
339 #endif /* NETWORK_H */