354 readlist[ readlen ] = socket |
354 readlist[ readlen ] = socket |
355 |
355 |
356 return handler, socket |
356 return handler, socket |
357 end |
357 end |
358 |
358 |
|
359 wraptlsclient = function( listener, socket, ip, serverport, clientport, mode, sslctx ) -- this function wraps a tls cleint |
|
360 |
|
361 local dispatch, disconnect = listener.listener, listener.disconnect |
|
362 |
|
363 --// transform socket to ssl object //-- |
|
364 |
|
365 local err |
|
366 |
|
367 socket:settimeout( 0 ) |
|
368 |
|
369 --// private closures of the object //-- |
|
370 |
|
371 local writequeue = { } -- buffer for messages to send |
|
372 |
|
373 local eol -- end of buffer |
|
374 |
|
375 local sstat, rstat = 0, 0 |
|
376 |
|
377 --// local import of socket methods //-- |
|
378 |
|
379 local send = socket.send |
|
380 local receive = socket.receive |
|
381 local close = socket.close |
|
382 --local shutdown = socket.shutdown |
|
383 |
|
384 --// public methods of the object //-- |
|
385 |
|
386 local handler = { } |
|
387 |
|
388 handler.getstats = function( ) |
|
389 return rstat, sstat |
|
390 end |
|
391 |
|
392 handler.listener = function( data, err ) |
|
393 return listener( handler, data, err ) |
|
394 end |
|
395 handler.ssl = function( ) |
|
396 return false |
|
397 end |
|
398 handler.send = function( _, data, i, j ) |
|
399 return send( socket, data, i, j ) |
|
400 end |
|
401 handler.receive = function( pattern, prefix ) |
|
402 return receive( socket, pattern, prefix ) |
|
403 end |
|
404 handler.shutdown = function( pattern ) |
|
405 --return shutdown( socket, pattern ) |
|
406 end |
|
407 handler.close = function( closed ) |
|
408 close( socket ) |
|
409 writelen = ( eol and removesocket( writelist, socket, writelen ) ) or writelen |
|
410 readlen = removesocket( readlist, socket, readlen ) |
|
411 socketlist[ socket ] = nil |
|
412 out_put "server.lua: closed handler and removed socket from list" |
|
413 end |
|
414 handler.ip = function( ) |
|
415 return ip |
|
416 end |
|
417 handler.serverport = function( ) |
|
418 return serverport |
|
419 end |
|
420 handler.clientport = function( ) |
|
421 return clientport |
|
422 end |
|
423 |
|
424 handler.write = function( data ) |
|
425 if not eol then |
|
426 writelen = writelen + 1 |
|
427 writelist[ writelen ] = socket |
|
428 eol = 0 |
|
429 end |
|
430 eol = eol + 1 |
|
431 writequeue[ eol ] = data |
|
432 end |
|
433 handler.writequeue = function( ) |
|
434 return writequeue |
|
435 end |
|
436 handler.socket = function( ) |
|
437 return socket |
|
438 end |
|
439 handler.mode = function( ) |
|
440 return mode |
|
441 end |
|
442 handler._receivedata = function( ) |
|
443 local data, err, part = receive( socket, mode ) -- receive data in "mode" |
|
444 if not err or ( err == "timeout" or err == "wantread" ) then -- received something |
|
445 local data = data or part or "" |
|
446 local count = #data * STAT_UNIT |
|
447 rstat = rstat + count |
|
448 receivestat = receivestat + count |
|
449 --out_put( "server.lua: read data '", data, "', error: ", err ) |
|
450 return dispatch( handler, data, err ) |
|
451 else -- connections was closed or fatal error |
|
452 out_put( "server.lua: client ", ip, ":", clientport, " error: ", err ) |
|
453 handler.close( ) |
|
454 disconnect( handler, err ) |
|
455 writequeue = nil |
|
456 handler = nil |
|
457 return false |
|
458 end |
|
459 end |
|
460 handler._dispatchdata = function( ) -- this function writes data to handlers |
|
461 local buffer = table_concat( writequeue, "", 1, eol ) |
|
462 local succ, err, byte = send( socket, buffer ) |
|
463 local count = ( succ or 0 ) * STAT_UNIT |
|
464 sstat = sstat + count |
|
465 sendstat = sendstat + count |
|
466 out_put( "server.lua: sended '", buffer, "', bytes: ", succ, ", error: ", err, ", part: ", byte, ", to: ", ip, ":", clientport ) |
|
467 if succ then -- sending succesful |
|
468 --writequeue = { } |
|
469 eol = nil |
|
470 writelen = removesocket( writelist, socket, writelen ) -- delete socket from writelist |
|
471 if handler.need_tls then |
|
472 out_put("server.lua: connection is ready for tls handshake"); |
|
473 handler.starttls(true); |
|
474 if handler.need_tls then |
|
475 out_put("server.lua: uh-oh... we still want tls, something must be wrong"); |
|
476 end |
|
477 end |
|
478 return true |
|
479 elseif byte and ( err == "timeout" or err == "wantwrite" ) then -- want write |
|
480 buffer = string_sub( buffer, byte + 1, -1 ) -- new buffer |
|
481 writequeue[ 1 ] = buffer -- insert new buffer in queue |
|
482 eol = 1 |
|
483 return true |
|
484 else -- connection was closed during sending or fatal error |
|
485 out_put( "server.lua: client ", ip, ":", clientport, " error: ", err ) |
|
486 handler.close( ) |
|
487 disconnect( handler, err ) |
|
488 writequeue = nil |
|
489 handler = nil |
|
490 return false |
|
491 end |
|
492 end |
|
493 |
|
494 handler.receivedata, handler.dispatchdata = handler._receivedata, handler._dispatchdata; |
|
495 -- // COMPAT // -- |
|
496 |
|
497 handler.getIp = handler.ip |
|
498 handler.getPort = handler.clientport |
|
499 |
|
500 --// handshake //-- |
|
501 |
|
502 local wrote, read |
|
503 |
|
504 handler.starttls = function (now) |
|
505 if not now then out_put("server.lua: we need to do tls, but delaying until later"); handler.need_tls = true; return; end |
|
506 out_put( "server.lua: attempting to start tls on "..tostring(socket) ) |
|
507 socket, err = ssl_wrap( socket, sslctx ) -- wrap socket |
|
508 out_put("sslwrapped socket is "..tostring(socket)); |
|
509 if err then |
|
510 out_put( "server.lua: ssl error: ", err ) |
|
511 return nil, nil, err -- fatal error |
|
512 end |
|
513 socket:settimeout( 1 ) |
|
514 send = socket.send |
|
515 receive = socket.receive |
|
516 close = socket.close |
|
517 handler.ssl = function( ) |
|
518 return true |
|
519 end |
|
520 handler.send = function( _, data, i, j ) |
|
521 return send( socket, data, i, j ) |
|
522 end |
|
523 handler.receive = function( pattern, prefix ) |
|
524 return receive( socket, pattern, prefix ) |
|
525 end |
|
526 |
|
527 handler.handshake = coroutine_wrap( function( client ) |
|
528 local err |
|
529 for i = 1, 10 do -- 10 handshake attemps |
|
530 _, err = client:dohandshake( ) |
|
531 if not err then |
|
532 out_put( "server.lua: ssl handshake done" ) |
|
533 writelen = ( wrote and removesocket( writelist, socket, writelen ) ) or writelen |
|
534 handler.receivedata = handler._receivedata -- when handshake is done, replace the handshake function with regular functions |
|
535 handler.dispatchdata = handler._dispatchdata |
|
536 handler.need_tls = nil |
|
537 socketlist[ client ] = handler |
|
538 readlen = readlen + 1 |
|
539 readlist[ readlen ] = client |
|
540 return true; |
|
541 else |
|
542 out_put( "server.lua: error during ssl handshake: ", err ) |
|
543 if err == "wantwrite" then |
|
544 if wrote == nil then |
|
545 writelen = writelen + 1 |
|
546 writelist[ writelen ] = client |
|
547 wrote = true |
|
548 end |
|
549 end |
|
550 coroutine_yield( handler, nil, err ) -- handshake not finished |
|
551 end |
|
552 end |
|
553 _ = err ~= "closed" and close( socket ) |
|
554 handler.close( ) |
|
555 disconnect( handler, err ) |
|
556 writequeue = nil |
|
557 handler = nil |
|
558 return false -- handshake failed |
|
559 end |
|
560 ) |
|
561 handler.receivedata = handler.handshake |
|
562 handler.dispatchdata = handler.handshake |
|
563 |
|
564 handler.handshake( socket ) -- do handshake |
|
565 end |
|
566 socketlist[ socket ] = handler |
|
567 readlen = readlen + 1 |
|
568 readlist[ readlen ] = socket |
|
569 |
|
570 return handler, socket |
|
571 end |
|
572 |
359 wraptcpclient = function( listener, socket, ip, serverport, clientport, mode ) -- this function wraps a socket |
573 wraptcpclient = function( listener, socket, ip, serverport, clientport, mode ) -- this function wraps a socket |
360 |
574 |
361 local dispatch, disconnect = listener.listener, listener.disconnect |
575 local dispatch, disconnect = listener.listener, listener.disconnect |
362 |
576 |
363 --// private closures of the object //-- |
577 --// private closures of the object //-- |