oyyd / encryptsocks

Encrypt your socks transmission.
BSD 3-Clause "New" or "Revised" License
141 stars 20 forks source link

unsupported method: #23

Closed shangxinbo closed 7 years ago

shangxinbo commented 7 years ago

使用localssjs -c cons.json 时出现unsupported method:错误,其中cons.json的配置如下 { "serverAddr": "s1.l3l.site", "serverPort": 31178, "localAddr": "127.0.0.1", "localPort": 1080, "pacServerPort": 8090, "password": "kingss.pw", "timeout": 600, "method": "aes-256-cfb",

"level": "warn", "localAddrIPv6": "::1", "serverAddrIPv6": "::1" }

oyyd commented 7 years ago
openssl list-message-digest-algorithms

看看你机器上的openssl支持情况

shangxinbo commented 7 years ago

我的是windows,这条命令不能执行

shangxinbo commented 7 years ago

请问一下下边的这段代码是什么意思,做什么用 if (!~data.indexOf(0x00, 2) && !~data.indexOf(0x02, 2)) { logger.warn(unsupported method: ${data.toString('hex')}); buf.writeUInt16BE(0x05FF); connection.write(buf); connection.end(); return -1; }

oyyd commented 7 years ago

socks5协议里面0x00是无需认证,0x02是用用户名密码认证,这里不支持其他认证方式,则会返回错误消息

shangxinbo commented 7 years ago

执行openssl list-message-digest-algorithms 得到以下结果 DSA DSA-SHA DSA-SHA1 => DSA DSA-SHA1-old => DSA-SHA1 DSS1 => DSA-SHA1 MD4 MD5 MDC2 RIPEMD160 RSA-MD4 => MD4 RSA-MD5 => MD5 RSA-MDC2 => MDC2 RSA-RIPEMD160 => RIPEMD160 RSA-SHA => SHA RSA-SHA1 => SHA1 RSA-SHA1-2 => RSA-SHA1 RSA-SHA224 => SHA224 RSA-SHA256 => SHA256 RSA-SHA384 => SHA384 RSA-SHA512 => SHA512 SHA SHA1 SHA224 SHA256 SHA384 SHA512 DSA DSA-SHA dsaWithSHA1 => DSA dss1 => DSA-SHA1 ecdsa-with-SHA1 MD4 md4WithRSAEncryption => MD4 MD5 md5WithRSAEncryption => MD5 MDC2 mdc2WithRSA => MDC2 ripemd => RIPEMD160 RIPEMD160 ripemd160WithRSA => RIPEMD160 rmd160 => RIPEMD160 SHA SHA1 sha1WithRSAEncryption => SHA1 SHA224 sha224WithRSAEncryption => SHA224 SHA256 sha256WithRSAEncryption => SHA256 SHA384 sha384WithRSAEncryption => SHA384 SHA512 sha512WithRSAEncryption => SHA512 shaWithRSAEncryption => SHA ssl2-md5 => MD5 ssl3-md5 => MD5 ssl3-sha1 => SHA1 whirlpool

shangxinbo commented 7 years ago

warn: unsupported method: 434f4e4e454354207777772e676f6f676c652e636f6d2e686b3a34343320485454502f312e310d0a486f73743a207777772e676f6f676c652e636f6d2e686b3a3434330d0a50726f78792d436f6e6e656374696f6e3a206b6565702d616c6976650d0a557365722d4167656e743a204d6f7a696c6c612f352e30202857696e646f7773204e542031302e303b2057696e36343b2078363429204170706c655765624b69742f3533372e333620284b48544d4c2c206c696b65204765636b6f29204368726f6d652f35352e302e323838332e3735205361666172692f3533372e33360d0a0d0a

oyyd commented 7 years ago
434f4e4e454354207777772e676f6f676c

这段不像是socks5的头部,你是用什么和localssjs通信的呢?

oyyd commented 7 years ago

@ShangXinbo 你是不是用的http proxy?

shangxinbo commented 7 years ago

@oyyd 我搞错代理协议了,不过请问一下我查阅了socks5的协议认证协议里还有一个GSSAPI可用,为什么不支持呢?

shangxinbo commented 7 years ago

@oyyd

if (forceAuth && data.indexOf(0x02, 2) >= 0) {
    method = 2;
  }

  if (!forceAuth && data.indexOf(0x00, 2) >= 0) {
    method = 0;
  }

  // allow `no authetication` or any usename/password
  if (method === -1) {
    // logger.warn(`unsupported method: ${data.toString('hex')}`);
    buf.writeUInt16BE(0x05FF);
    connection.write(buf);
    connection.end();
    return -1;
  }

  buf.writeUInt16BE(0x0500);
  connection.write(buf);

  return method === 0 ? 1 : 3;

看你这里是验证认证方式时直接给客户端返回的是0x0500,为什么不可以是0x0502呢,如果客户端就是用的用户名认证方式会出现什么问题呢,不需要认证兼容用户名密码认证方式是么?

oyyd commented 7 years ago

因为实际上ss利用的是服务器和客户端的password作为验证依据,即便是支持多用户利用的也是password和port的对应。而使用socks5中的认证机制只对特定场景有意义(如果把socks5认证放在海外那整套ss就相当于明文传递,还是容易被识别)。现阶段大多数ss的实现应该都没有支持socks5的认证

oyyd commented 7 years ago

@ShangXinbo 其实我还是挺希望支持http proxy的,在local客户端上,不知道你有没有兴趣尝试实现,提交个PR

shangxinbo commented 7 years ago

@oyyd http proxy 相较于socks 来对我说还没有太大需求,如果有时间我会考虑一下

shangxinbo commented 7 years ago

@oyyd 对于你上边所说的认证协议的解释我可以理解成,不管client提出什么协议,localserver 都会按不需要认证的方式进行握手通信么?请解释一下buf.writeUInt16BE(0x0500);这里为什么不通过客户端请求的认证方式做一个逻辑判断的原因好么

shangxinbo commented 7 years ago

why not ?

            const buf = new Buffer(2);
            if (data.indexOf(0x02, 2) >= 0){           //用户名密码认证
                buf.writeUInt16BE(0x0502);
                stage = 3;

            }else if (data.indexOf(0x00, 2) >= 0){     //不需要认证
                buf.writeUInt16BE(0x0500);
                stage = 1;
            }else {
                buf.writeUInt16BE(0x05FF);             //没有可用的认证方式,连接终止
                stage = -1;
            }
            connect.write(buf);
oyyd commented 7 years ago

可以有,这类问题的通常回答都是 1. 对我没有应用场景 2. 没时间

shangxinbo commented 7 years ago

是时候考虑一下http proxy了

shangxinbo commented 7 years ago

我遵照你的意思写了搞了一层http proxy 并且做了一层socks tunnel 断线重连shadowsocks服务器节点,这样是可以简单的保证高可用,对多节点时造成不浪费,不过我感觉我的算法并不稳定,但还没有想到好的方法调试,不管怎么说有很多东西借鉴了该库,我的项目地址cardinal,命名cardinal的意思是"北美红雀",就是《angry birds》里的主人公,旨在“GWF的破坏者”。由于我的初衷是纯client端的实现,server端代码及UDP,还有auth验证等部分对我来说都是冗余的,所以并没有pr ,见谅!

oyyd commented 7 years ago

不用太在意形式,也不需要和一些事情牵扯上去,能从中有所收获就是最好的。