-
Notifications
You must be signed in to change notification settings - Fork 63
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
require xray-core v1.3.0 Signed-off-by: Teddysun <[email protected]>
- Loading branch information
Showing
13 changed files
with
1,322 additions
and
3 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,3 @@ | ||
xray-plugin* | ||
/bin/ | ||
/.idea/ |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,6 +1,8 @@ | ||
MIT License | ||
|
||
Copyright (c) 2021 Teddysun | ||
Copyright (c) 2019 by Max Lv <[email protected]> | ||
Copyright (C) 2019 by Mygod Studio <[email protected]> | ||
Copyright (c) 2021 by Teddysun <[email protected]> | ||
|
||
Permission is hereby granted, free of charge, to any person obtaining a copy | ||
of this software and associated documentation files (the "Software"), to deal | ||
|
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,2 +1,68 @@ | ||
# xray-plugin | ||
A SIP003 plugin based on xray | ||
# Yet another SIP003 plugin for shadowsocks, based on xray | ||
|
||
## Build | ||
|
||
* `go build` | ||
|
||
## Usage | ||
|
||
See command line args for advanced usages. | ||
|
||
### Shadowsocks over websocket (HTTP) | ||
|
||
On your server | ||
|
||
```sh | ||
ss-server -c config.json -p 80 --plugin xray-plugin --plugin-opts "server" | ||
``` | ||
|
||
On your client | ||
|
||
```sh | ||
ss-local -c config.json -p 80 --plugin xray-plugin | ||
``` | ||
|
||
### Shadowsocks over websocket (HTTPS) | ||
|
||
On your server | ||
|
||
```sh | ||
ss-server -c config.json -p 443 --plugin xray-plugin --plugin-opts "server;tls;host=mydomain.me" | ||
``` | ||
|
||
On your client | ||
|
||
```sh | ||
ss-local -c config.json -p 443 --plugin xray-plugin --plugin-opts "tls;host=mydomain.me" | ||
``` | ||
|
||
### Shadowsocks over quic | ||
|
||
On your server | ||
|
||
```sh | ||
ss-server -c config.json -p 443 --plugin xray-plugin --plugin-opts "server;mode=quic;host=mydomain.me" | ||
``` | ||
|
||
On your client | ||
|
||
```sh | ||
ss-local -c config.json -p 443 --plugin xray-plugin --plugin-opts "mode=quic;host=mydomain.me" | ||
``` | ||
|
||
### Issue a cert for TLS and QUIC | ||
|
||
xray-plugin will look for TLS certificates signed by [acme.sh](https://github.com/Neilpang/acme.sh) by default. | ||
Here's some sample commands for issuing a certificate using CloudFlare. | ||
You can find commands for issuing certificates for other DNS providers at acme.sh. | ||
|
||
```sh | ||
curl https://get.acme.sh | sh | ||
~/.acme.sh/acme.sh --issue --dns dns_cf -d mydomain.me | ||
``` | ||
|
||
Alternatively, you can specify path to your certificates using option `cert` and `key`. | ||
|
||
### Use `certRaw` to pass certificate | ||
|
||
Instead of using `cert` to pass the certificate file, `certRaw` could be used to pass in PEM format certificate, that is the content between `-----BEGIN CERTIFICATE-----` and `-----END CERTIFICATE-----` without the line breaks. |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,196 @@ | ||
package main | ||
|
||
import ( | ||
"bytes" | ||
"fmt" | ||
"net" | ||
"os" | ||
"sort" | ||
"strings" | ||
) | ||
|
||
func isIPv6(str string) bool { | ||
ip := net.ParseIP(str) | ||
return ip != nil && strings.Contains(str, ":") | ||
} | ||
|
||
// Key–value mappings for the representation of client and server options. | ||
|
||
// Args maps a string key to a list of values. It is similar to url.Values. | ||
type Args map[string][]string | ||
|
||
// Get the first value associated with the given key. If there are any values | ||
// associated with the key, the value return has the value and ok is set to | ||
// true. If there are no values for the given key, value is "" and ok is false. | ||
// If you need access to multiple values, use the map directly. | ||
func (args Args) Get(key string) (value string, ok bool) { | ||
if args == nil { | ||
return "", false | ||
} | ||
vals, ok := args[key] | ||
if !ok || len(vals) == 0 { | ||
return "", false | ||
} | ||
return vals[0], true | ||
} | ||
|
||
// Append value to the list of values for key. | ||
func (args Args) Add(key, value string) { | ||
args[key] = append(args[key], value) | ||
} | ||
|
||
// Return the index of the next unescaped byte in s that is in the term set, or | ||
// else the length of the string if no terminators appear. Additionally return | ||
// the unescaped string up to the returned index. | ||
func indexUnescaped(s string, term []byte) (int, string, error) { | ||
var i int | ||
unesc := make([]byte, 0) | ||
for i = 0; i < len(s); i++ { | ||
b := s[i] | ||
// A terminator byte? | ||
if bytes.IndexByte(term, b) != -1 { | ||
break | ||
} | ||
if b == '\\' { | ||
i++ | ||
if i >= len(s) { | ||
return 0, "", fmt.Errorf("nothing following final escape in %q", s) | ||
} | ||
b = s[i] | ||
} | ||
unesc = append(unesc, b) | ||
} | ||
return i, string(unesc), nil | ||
} | ||
|
||
// Parse SS_PLUGIN options from environment variables | ||
func parseEnv() (opts Args, err error) { | ||
opts = make(Args) | ||
ss_remote_host := os.Getenv("SS_REMOTE_HOST") | ||
ss_remote_port := os.Getenv("SS_REMOTE_PORT") | ||
ss_local_host := os.Getenv("SS_LOCAL_HOST") | ||
ss_local_port := os.Getenv("SS_LOCAL_PORT") | ||
if len(ss_remote_host) == 0 { | ||
return | ||
} | ||
if len(ss_remote_port) == 0 { | ||
return | ||
} | ||
if len(ss_local_host) == 0 { | ||
return | ||
} | ||
if len(ss_local_port) == 0 { | ||
return | ||
} | ||
|
||
opts.Add("remoteAddr", ss_remote_host) | ||
opts.Add("remotePort", ss_remote_port) | ||
opts.Add("localAddr", ss_local_host) | ||
opts.Add("localPort", ss_local_port) | ||
|
||
ss_plugin_options := os.Getenv("SS_PLUGIN_OPTIONS") | ||
if len(ss_plugin_options) > 0 { | ||
other_opts, err := parsePluginOptions(ss_plugin_options) | ||
if err != nil { | ||
return nil, err | ||
} | ||
for k, v := range other_opts { | ||
opts[k] = v | ||
} | ||
} | ||
return opts, nil | ||
} | ||
|
||
// Parse a name–value mapping as from SS_PLUGIN_OPTIONS. | ||
// | ||
// "<value> is a k=v string value with options that are to be passed to the | ||
// transport. semicolons, equal signs and backslashes must be escaped | ||
// with a backslash." | ||
// Example: secret=nou;cache=/tmp/cache;secret=yes | ||
func parsePluginOptions(s string) (opts Args, err error) { | ||
opts = make(Args) | ||
if len(s) == 0 { | ||
return | ||
} | ||
i := 0 | ||
for { | ||
var key, value string | ||
var offset, begin int | ||
|
||
if i >= len(s) { | ||
break | ||
} | ||
begin = i | ||
// Read the key. | ||
offset, key, err = indexUnescaped(s[i:], []byte{'=', ';'}) | ||
if err != nil { | ||
return | ||
} | ||
if len(key) == 0 { | ||
err = fmt.Errorf("empty key in %q", s[begin:i]) | ||
return | ||
} | ||
i += offset | ||
// End of string or no equals sign? | ||
if i >= len(s) || s[i] != '=' { | ||
opts.Add(key, "1") | ||
// Skip the semicolon. | ||
i++ | ||
continue | ||
} | ||
// Skip the equals sign. | ||
i++ | ||
// Read the value. | ||
offset, value, err = indexUnescaped(s[i:], []byte{';'}) | ||
if err != nil { | ||
return | ||
} | ||
i += offset | ||
opts.Add(key, value) | ||
// Skip the semicolon. | ||
i++ | ||
} | ||
return opts, nil | ||
} | ||
|
||
// Escape backslashes and all the bytes that are in set. | ||
func backslashEscape(s string, set []byte) string { | ||
var buf bytes.Buffer | ||
for _, b := range []byte(s) { | ||
if b == '\\' || bytes.IndexByte(set, b) != -1 { | ||
buf.WriteByte('\\') | ||
} | ||
buf.WriteByte(b) | ||
} | ||
return buf.String() | ||
} | ||
|
||
// Encode a name–value mapping so that it is suitable to go in the ARGS option | ||
// of an SMETHOD line. The output is sorted by key. The "ARGS:" prefix is not | ||
// added. | ||
// | ||
// "Equal signs and commas [and backslashes] must be escaped with a backslash." | ||
func encodeSmethodArgs(args Args) string { | ||
if args == nil { | ||
return "" | ||
} | ||
|
||
keys := make([]string, 0, len(args)) | ||
for key := range args { | ||
keys = append(keys, key) | ||
} | ||
sort.Strings(keys) | ||
|
||
escape := func(s string) string { | ||
return backslashEscape(s, []byte{'=', ','}) | ||
} | ||
|
||
var pairs []string | ||
for _, key := range keys { | ||
for _, value := range args[key] { | ||
pairs = append(pairs, escape(key)+"="+escape(value)) | ||
} | ||
} | ||
|
||
return strings.Join(pairs, ",") | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,88 @@ | ||
#!/bin/bash | ||
sum="sha1sum" | ||
|
||
if ! hash sha1sum 2>/dev/null; then | ||
if ! hash shasum 2>/dev/null; then | ||
echo "I can't see 'sha1sum' or 'shasum'" | ||
echo "Please install one of them!" | ||
exit | ||
fi | ||
sum="shasum" | ||
fi | ||
|
||
[[ -z $upx ]] && upx="echo pending" | ||
if [[ $upx == "echo pending" ]] && hash upx 2>/dev/null; then | ||
upx="upx -9" | ||
fi | ||
|
||
VERSION=$(git describe --tags) | ||
LDFLAGS="-X main.VERSION=$VERSION -s -w" | ||
GCFLAGS="" | ||
|
||
OSES=(linux darwin windows freebsd) | ||
ARCHS=(amd64 386) | ||
|
||
mkdir bin | ||
|
||
for os in ${OSES[@]}; do | ||
for arch in ${ARCHS[@]}; do | ||
# Go 1.15 drops support for 32-bit binaries on macOS, iOS, iPadOS, watchOS, and tvOS (the darwin/386 and darwin/arm ports) | ||
# Reference URL: https://tip.golang.org/doc/go1.15#darwin | ||
if [ "$os" == "darwin" ] && [ "$arch" == "386" ]; then | ||
continue | ||
fi | ||
suffix="" | ||
if [ "$os" == "windows" ]; then | ||
suffix=".exe" | ||
fi | ||
env CGO_ENABLED=0 GOOS=$os GOARCH=$arch go build -v -ldflags "$LDFLAGS" -gcflags "$GCFLAGS" -o xray-plugin_${os}_${arch}${suffix} | ||
$upx xray-plugin_${os}_${arch}${suffix} >/dev/null | ||
tar -zcf bin/xray-plugin-${os}-${arch}-$VERSION.tar.gz xray-plugin_${os}_${arch}${suffix} | ||
$sum bin/xray-plugin-${os}-${arch}-$VERSION.tar.gz | ||
done | ||
done | ||
|
||
# ARM | ||
ARMS=(5 6 7) | ||
for v in ${ARMS[@]}; do | ||
env CGO_ENABLED=0 GOOS=linux GOARCH=arm GOARM=$v go build -v -ldflags "$LDFLAGS" -gcflags "$GCFLAGS" -o xray-plugin_linux_arm$v | ||
done | ||
$upx xray-plugin_linux_arm* >/dev/null | ||
tar -zcf bin/xray-plugin-linux-arm-$VERSION.tar.gz xray-plugin_linux_arm* | ||
$sum bin/xray-plugin-linux-arm-$VERSION.tar.gz | ||
|
||
# ARM64 (ARMv8 or aarch64) | ||
env CGO_ENABLED=0 GOOS=linux GOARCH=arm64 go build -v -ldflags "$LDFLAGS" -gcflags "$GCFLAGS" -o xray-plugin_linux_arm64 | ||
$upx xray-plugin_linux_arm64 >/dev/null | ||
tar -zcf bin/xray-plugin-linux-arm64-$VERSION.tar.gz xray-plugin_linux_arm64 | ||
$sum bin/xray-plugin-linux-arm64-$VERSION.tar.gz | ||
|
||
# MIPS | ||
MIPSS=(mips mipsle) | ||
for v in ${MIPSS[@]}; do | ||
env CGO_ENABLED=0 GOOS=linux GOARCH=$v go build -v -ldflags "$LDFLAGS" -gcflags "$GCFLAGS" -o xray-plugin_linux_$v | ||
env CGO_ENABLED=0 GOOS=linux GOARCH=$v GOMIPS=softfloat go build -ldflags "$LDFLAGS" -gcflags "$GCFLAGS" -o xray-plugin_linux_${v}_sf | ||
done | ||
$upx xray-plugin_linux_mips* >/dev/null | ||
tar -zcf bin/xray-plugin-linux-mips-$VERSION.tar.gz xray-plugin_linux_mips* | ||
$sum bin/xray-plugin-linux-mips-$VERSION.tar.gz | ||
|
||
# MIPS64 | ||
MIPS64S=(mips64 mips64le) | ||
for v in ${MIPS64S[@]}; do | ||
env CGO_ENABLED=0 GOOS=linux GOARCH=$v go build -v -ldflags "$LDFLAGS" -gcflags "$GCFLAGS" -o xray-plugin_linux_$v | ||
done | ||
tar -zcf bin/xray-plugin-linux-mips64-$VERSION.tar.gz xray-plugin_linux_mips64* | ||
$sum bin/xray-plugin-linux-mips64-$VERSION.tar.gz | ||
|
||
# ppc64le | ||
env CGO_ENABLED=0 GOOS=linux GOARCH=ppc64le go build -v -ldflags "$LDFLAGS" -gcflags "$GCFLAGS" -o xray-plugin_linux_ppc64le | ||
$upx xray-plugin_linux_ppc64le >/dev/null | ||
tar -zcf bin/xray-plugin-linux-ppc64le-$VERSION.tar.gz xray-plugin_linux_ppc64le | ||
$sum bin/xray-plugin-linux-ppc64le-$VERSION.tar.gz | ||
|
||
# s390x | ||
env CGO_ENABLED=0 GOOS=linux GOARCH=s390x go build -v -ldflags "$LDFLAGS" -gcflags "$GCFLAGS" -o xray-plugin_linux_s390x | ||
$upx xray-plugin_linux_s390x >/dev/null | ||
tar -zcf bin/xray-plugin-linux-s390x-$VERSION.tar.gz xray-plugin_linux_s390x | ||
$sum bin/xray-plugin-linux-s390x-$VERSION.tar.gz |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,9 @@ | ||
package main | ||
|
||
import "github.com/xtls/xray-core/common/errors" | ||
|
||
type errPathObjHolder struct{} | ||
|
||
func newError(values ...interface{}) *errors.Error { | ||
return errors.New(values...).WithPathObj(errPathObjHolder{}) | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,8 @@ | ||
module github.com/teddysun/xray-plugin | ||
|
||
require ( | ||
github.com/golang/protobuf v1.4.3 | ||
github.com/xtls/xray-core v1.3.0 | ||
) | ||
|
||
go 1.15 |
Oops, something went wrong.