forked from x/ContextOS
mac opt script engine
This commit is contained in:
parent
e4a597678b
commit
df905f1907
12
etc/init.shy
12
etc/init.shy
@ -1,9 +1,13 @@
|
|||||||
scan_file etc/demo.shy
|
~cli config debug on
|
||||||
|
|
||||||
return
|
return
|
||||||
|
scan_file etc/demo.shy
|
||||||
|
echo "who"
|
||||||
|
~web
|
||||||
|
command add get "https://chat.shylinux.com"
|
||||||
source etc/local.shy
|
source etc/local.shy
|
||||||
|
|
||||||
~aaa
|
~aaa
|
||||||
login root root
|
login root root
|
||||||
~web
|
|
||||||
command add get "https://chat.shylinux.com"
|
~yac
|
||||||
|
scan_file etc/demo.shy demo_file
|
||||||
|
@ -215,6 +215,24 @@ func (cli *CLI) Begin(m *ctx.Message, arg ...string) ctx.Server { // {{{
|
|||||||
|
|
||||||
// }}}
|
// }}}
|
||||||
func (cli *CLI) Start(m *ctx.Message, arg ...string) bool { // {{{
|
func (cli *CLI) Start(m *ctx.Message, arg ...string) bool { // {{{
|
||||||
|
if len(arg) > 0 && arg[0] == "scan_file" {
|
||||||
|
cli.Context.Exit = make(chan bool)
|
||||||
|
m.Find("yac").Call(func(cmd *ctx.Message) *ctx.Message {
|
||||||
|
if cmd.Detail(0) == "scan_end" {
|
||||||
|
msg := m.Spawn()
|
||||||
|
cli.Exit <- true
|
||||||
|
m.Target().Close(msg)
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
cmd.Source(m.Target())
|
||||||
|
cmd.Target(m.Target())
|
||||||
|
cmd.Cmd()
|
||||||
|
return nil
|
||||||
|
}, "scan_file", arg[1])
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
|
||||||
m.Sesss("cli", m)
|
m.Sesss("cli", m)
|
||||||
cli.Caches["#"] = &ctx.Cache{Name: "参数个数", Value: fmt.Sprintf("%d", len(arg)), Help: "参数个数"}
|
cli.Caches["#"] = &ctx.Cache{Name: "参数个数", Value: fmt.Sprintf("%d", len(arg)), Help: "参数个数"}
|
||||||
for i, v := range arg {
|
for i, v := range arg {
|
||||||
@ -251,13 +269,29 @@ func (cli *CLI) Start(m *ctx.Message, arg ...string) bool { // {{{
|
|||||||
|
|
||||||
cli.nfs = m.Sesss("nfs", "nfs")
|
cli.nfs = m.Sesss("nfs", "nfs")
|
||||||
if m.Has("stdio") {
|
if m.Has("stdio") {
|
||||||
cli.nfs.Cmd("scan", m.Cap("stream", "stdio"), m.Spawn(m.Target()).Cmd("source", m.Cap("init.shy")).Get("result"))
|
m.Spawn().Cmd("scan_file", m.Cap("stream", m.Cap("init.shy")))
|
||||||
|
cli.Context.Exit = make(chan bool)
|
||||||
|
m.Find("yac").Call(func(cmd *ctx.Message) *ctx.Message {
|
||||||
|
if cmd.Detail(0) == "scan_end" {
|
||||||
|
msg := m.Spawn()
|
||||||
|
cli.Exit <- true
|
||||||
|
m.Target().Close(msg)
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
cmd.Source(m.Target())
|
||||||
|
cmd.Target(m.Target())
|
||||||
|
cmd.Cmd()
|
||||||
|
return nil
|
||||||
|
}, "scan_file", m.Cap("stream", "stdio"))
|
||||||
} else {
|
} else {
|
||||||
if _, e := os.Stat(m.Cap("init.shy")); e == nil {
|
if _, e := os.Stat(m.Cap("init.shy")); e == nil {
|
||||||
|
// m.Spawn().Cmd("scan_file", m.Cap("stream", m.Cap("init.shy")))
|
||||||
cli.nfs.Cmd("scan", m.Cap("stream", m.Cap("init.shy")))
|
cli.nfs.Cmd("scan", m.Cap("stream", m.Cap("init.shy")))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}()
|
}()
|
||||||
|
return false
|
||||||
}
|
}
|
||||||
|
|
||||||
m.Deal(func(msg *ctx.Message, arg ...string) bool {
|
m.Deal(func(msg *ctx.Message, arg ...string) bool {
|
||||||
@ -293,8 +327,6 @@ func (cli *CLI) Close(m *ctx.Message, arg ...string) bool { // {{{
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return false
|
|
||||||
|
|
||||||
return true
|
return true
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -839,14 +871,8 @@ var Index = &ctx.Context{Name: "cli", Help: "管理中心",
|
|||||||
m.Echo("%s", strings.Join(arg, ""))
|
m.Echo("%s", strings.Join(arg, ""))
|
||||||
}},
|
}},
|
||||||
"scan_file": &ctx.Command{Name: "scan_file", Help: "函数调用, name: 函数名, arg: 参数", Hand: func(m *ctx.Message, c *ctx.Context, key string, arg ...string) {
|
"scan_file": &ctx.Command{Name: "scan_file", Help: "函数调用, name: 函数名, arg: 参数", Hand: func(m *ctx.Message, c *ctx.Context, key string, arg ...string) {
|
||||||
m.Find("yac").Call(func(cmd *ctx.Message) *ctx.Message {
|
m.Start(arg[0], "cli", "scan_file", arg[0])
|
||||||
cmd.Source(m.Target())
|
<-m.Target().Exit
|
||||||
cmd.Target(m.Target())
|
|
||||||
m.Log("fuck", nil, "------cmd run- %v %s", cmd.Meta, cmd.Hand)
|
|
||||||
cmd.Cmd()
|
|
||||||
m.Log("fuck", nil, "------cmd run- %v", cmd.Meta)
|
|
||||||
return nil
|
|
||||||
}, "scan_file", arg[0])
|
|
||||||
}},
|
}},
|
||||||
},
|
},
|
||||||
Index: map[string]*ctx.Context{
|
Index: map[string]*ctx.Context{
|
||||||
|
@ -958,7 +958,11 @@ func (m *Message) Back(msg *Message) *Message { // {{{
|
|||||||
return m
|
return m
|
||||||
}
|
}
|
||||||
|
|
||||||
m.Log("cb", nil, "%d %v %v", msg.code, msg.Meta["result"], msg.Meta["append"])
|
if msg.Hand {
|
||||||
|
m.Log("cb", nil, "%d %v %v", msg.code, msg.Meta["result"], msg.Meta["append"])
|
||||||
|
} else {
|
||||||
|
m.Log("cb", nil, "%d %v %v", msg.code, msg.Meta["detail"], msg.Meta["option"])
|
||||||
|
}
|
||||||
|
|
||||||
m.callback.ncall++
|
m.callback.ncall++
|
||||||
if sub := m.callback.hand(msg); sub != nil && m.message != nil && m.message != m {
|
if sub := m.callback.hand(msg); sub != nil && m.message != nil && m.message != m {
|
||||||
|
@ -93,7 +93,8 @@ func (nfs *NFS) prompt(arg ...string) { // {{{
|
|||||||
rest = arg[1]
|
rest = arg[1]
|
||||||
}
|
}
|
||||||
|
|
||||||
if nfs.color(nfs.cli.Conf("PS1"), nfs.Confi("pscolor")).color(line).color(rest); len(rest) > 0 {
|
// if nfs.color(nfs.cli.Conf("PS1"), nfs.Confi("pscolor")).color(line).color(rest); len(rest) > 0 {
|
||||||
|
if fmt.Fprintf(nfs.out, "> %s%s", line, rest); len(rest) > 0 {
|
||||||
fmt.Fprintf(nfs.out, "\033[%dD", len(rest))
|
fmt.Fprintf(nfs.out, "\033[%dD", len(rest))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -198,8 +199,10 @@ func (nfs *NFS) Read(p []byte) (n int, err error) { // {{{
|
|||||||
if nfs.Cap("stream") != "stdio" {
|
if nfs.Cap("stream") != "stdio" {
|
||||||
return nfs.in.Read(p)
|
return nfs.in.Read(p)
|
||||||
}
|
}
|
||||||
|
nfs.Log("fuck", nil, "why")
|
||||||
|
|
||||||
nfs.width, nfs.height = termbox.Size()
|
nfs.width, nfs.height = termbox.Size()
|
||||||
|
nfs.Log("fuck", nil, "why %d %d", nfs.width, nfs.height)
|
||||||
|
|
||||||
buf := make([]rune, 0, 1024)
|
buf := make([]rune, 0, 1024)
|
||||||
rest := make([]rune, 0, 1024)
|
rest := make([]rune, 0, 1024)
|
||||||
@ -435,10 +438,35 @@ func (nfs *NFS) Begin(m *ctx.Message, arg ...string) ctx.Server { // {{{
|
|||||||
// }}}
|
// }}}
|
||||||
func (nfs *NFS) Start(m *ctx.Message, arg ...string) bool { // {{{
|
func (nfs *NFS) Start(m *ctx.Message, arg ...string) bool { // {{{
|
||||||
if len(arg) > 0 && arg[0] == "scan_file" {
|
if len(arg) > 0 && arg[0] == "scan_file" {
|
||||||
|
if arg[1] == "stdio" {
|
||||||
|
if in, ok := m.Data["in"]; ok {
|
||||||
|
nfs.in = in.(*os.File)
|
||||||
|
}
|
||||||
|
if out, ok := m.Data["out"]; ok {
|
||||||
|
nfs.out = out.(*os.File)
|
||||||
|
}
|
||||||
|
bio := bufio.NewScanner(nfs)
|
||||||
|
nfs.Message = m
|
||||||
|
termbox.Init()
|
||||||
|
defer termbox.Close()
|
||||||
|
|
||||||
|
m.Cap("stream", "stdio")
|
||||||
|
nfs.prompt()
|
||||||
|
for bio.Scan() {
|
||||||
|
text := bio.Text() + "; "
|
||||||
|
m.Result(0, 0, len(text))
|
||||||
|
m.Put("append", "0", text)
|
||||||
|
m.Back(m)
|
||||||
|
nfs.prompt()
|
||||||
|
}
|
||||||
|
|
||||||
|
return true
|
||||||
|
}
|
||||||
|
|
||||||
in, ok := m.Optionv("in").(*os.File)
|
in, ok := m.Optionv("in").(*os.File)
|
||||||
m.Assert(ok)
|
m.Assert(ok)
|
||||||
|
|
||||||
for {
|
for !m.Options("scan_end") {
|
||||||
buf := make([]byte, m.Confi("buffer_size"))
|
buf := make([]byte, m.Confi("buffer_size"))
|
||||||
n, e := in.Read(buf)
|
n, e := in.Read(buf)
|
||||||
if e != nil && e != io.EOF {
|
if e != nil && e != io.EOF {
|
||||||
@ -454,7 +482,7 @@ func (nfs *NFS) Start(m *ctx.Message, arg ...string) bool { // {{{
|
|||||||
break
|
break
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return false
|
return true
|
||||||
}
|
}
|
||||||
|
|
||||||
m.Target().Sessions["nfs"] = m
|
m.Target().Sessions["nfs"] = m
|
||||||
@ -641,22 +669,28 @@ func (nfs *NFS) Start(m *ctx.Message, arg ...string) bool { // {{{
|
|||||||
|
|
||||||
for text = nfs.buf[pos] + "\n"; text != ""; {
|
for text = nfs.buf[pos] + "\n"; text != ""; {
|
||||||
|
|
||||||
line := m.Spawn(yac.Target())
|
if true {
|
||||||
line.Optioni("pos", pos)
|
m.Result(0, 0, len(text))
|
||||||
line.Options("stdio", true)
|
m.Put("append", fmt.Sprintf("%d", len(text)), text)
|
||||||
line.Put("option", "cli", cli.Target())
|
m.Back(m)
|
||||||
text = line.Cmd("parse", "line", "void", text).Get("result")
|
} else {
|
||||||
cli.Target(line.Data["cli"].(*ctx.Context))
|
line := m.Spawn(yac.Target())
|
||||||
if line.Has("return") {
|
line.Optioni("pos", pos)
|
||||||
goto out
|
line.Options("stdio", true)
|
||||||
}
|
line.Put("option", "cli", cli.Target())
|
||||||
if line.Has("back") {
|
text = line.Cmd("parse", "line", "void", text).Get("result")
|
||||||
pos = line.Appendi("back")
|
cli.Target(line.Data["cli"].(*ctx.Context))
|
||||||
|
if line.Has("return") {
|
||||||
|
goto out
|
||||||
|
}
|
||||||
|
if line.Has("back") {
|
||||||
|
pos = line.Appendi("back")
|
||||||
|
}
|
||||||
|
if result := strings.TrimRight(strings.Join(line.Meta["result"][1:len(line.Meta["result"])-1], ""), "\n"); len(result) > 0 {
|
||||||
|
nfs.print("%s", result+"\n")
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if result := strings.TrimRight(strings.Join(line.Meta["result"][1:len(line.Meta["result"])-1], ""), "\n"); len(result) > 0 {
|
|
||||||
nfs.print("%s", result+"\n")
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -714,14 +748,21 @@ var Index = &ctx.Context{Name: "nfs", Help: "存储中心",
|
|||||||
// }}}
|
// }}}
|
||||||
}},
|
}},
|
||||||
"nfs_help": &ctx.Config{Name: "nfs_help", Value: "file", Help: "默认模块帮助"},
|
"nfs_help": &ctx.Config{Name: "nfs_help", Value: "file", Help: "默认模块帮助"},
|
||||||
"buffer_size": &ctx.Config{Name: "buffer_size", Value: "16", Help: "缓存区大小"},
|
"buffer_size": &ctx.Config{Name: "buffer_size", Value: "1024", Help: "缓存区大小"},
|
||||||
},
|
},
|
||||||
Commands: map[string]*ctx.Command{
|
Commands: map[string]*ctx.Command{
|
||||||
"scan_file": &ctx.Command{Name: "scan_file filename", Help: "扫描文件, filename: 文件名", Hand: func(m *ctx.Message, c *ctx.Context, key string, arg ...string) {
|
"scan_file": &ctx.Command{Name: "scan_file filename", Help: "扫描文件, filename: 文件名", Hand: func(m *ctx.Message, c *ctx.Context, key string, arg ...string) {
|
||||||
if _, ok := m.Target().Server.(*NFS); m.Assert(ok) { // {{{
|
if _, ok := m.Target().Server.(*NFS); m.Assert(ok) { // {{{
|
||||||
f, e := os.Open(arg[0])
|
if arg[0] == "stdio" {
|
||||||
m.Assert(e)
|
m.Put("option", "in", os.Stdin)
|
||||||
m.Put("option", "in", f).Start(m.Confx("nfs_name", arg, 0), m.Confx("nfs_help", arg, 1), "scan_file", arg[0])
|
m.Put("option", "out", os.Stdout)
|
||||||
|
} else {
|
||||||
|
f, e := os.Open(arg[0])
|
||||||
|
m.Assert(e)
|
||||||
|
m.Put("option", "in", f)
|
||||||
|
}
|
||||||
|
|
||||||
|
m.Start(m.Confx("nfs_name", arg, 0), m.Confx("nfs_help", arg, 1), "scan_file", arg[0])
|
||||||
} // }}}
|
} // }}}
|
||||||
}},
|
}},
|
||||||
"buffer": &ctx.Command{Name: "buffer [index string]", Help: "扫描文件, file: 文件名", Hand: func(m *ctx.Message, c *ctx.Context, key string, arg ...string) {
|
"buffer": &ctx.Command{Name: "buffer [index string]", Help: "扫描文件, file: 文件名", Hand: func(m *ctx.Message, c *ctx.Context, key string, arg ...string) {
|
||||||
|
@ -3,6 +3,7 @@ package yac // {{{
|
|||||||
import ( // {{{
|
import ( // {{{
|
||||||
"contexts"
|
"contexts"
|
||||||
"fmt"
|
"fmt"
|
||||||
|
"io"
|
||||||
"strconv"
|
"strconv"
|
||||||
"strings"
|
"strings"
|
||||||
)
|
)
|
||||||
@ -258,7 +259,8 @@ func (yac *YAC) parse(m *ctx.Message, cli *ctx.Context, page, void int, line str
|
|||||||
|
|
||||||
// }}}
|
// }}}
|
||||||
func (yac *YAC) scan(m *ctx.Message, page int, void int, line string) (string, []string) { // {{{
|
func (yac *YAC) scan(m *ctx.Message, page int, void int, line string) (string, []string) { // {{{
|
||||||
m.Log("fuck", nil, "begin--%v-----%v", page, yac.word[page])
|
level := m.Optioni("level2")
|
||||||
|
m.Optioni("level2", level+1)
|
||||||
if line == "" { //加载数据
|
if line == "" { //加载数据
|
||||||
if data, ok := m.Optionv("data").(chan []byte); ok {
|
if data, ok := m.Optionv("data").(chan []byte); ok {
|
||||||
if buf := <-data; len(buf) > 0 {
|
if buf := <-data; len(buf) > 0 {
|
||||||
@ -266,31 +268,49 @@ func (yac *YAC) scan(m *ctx.Message, page int, void int, line string) (string, [
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
m.Assert(line != "")
|
||||||
|
|
||||||
hash, word := 0, []string{}
|
hash, word := 0, []string{}
|
||||||
for star, s := 0, page; s != 0 && len(line) > 0; {
|
for star, s := 0, page; s != 0 && len(line) > 0; {
|
||||||
line = m.Sesss("lex", "lex").Cmd("scan", line, yac.name(void)).Result(1)
|
lex := m.Sesss("lex", "lex").Cmd("scan", line, yac.name(void))
|
||||||
lex := m.Sesss("lex", "lex").Cmd("scan", line, yac.name(s))
|
|
||||||
|
|
||||||
if lex.Result(0) == "-1" { //加载数据
|
if lex.Result(0) == "-1" { //加载数据
|
||||||
|
if next, ok := m.Optionv("next").(chan bool); ok {
|
||||||
|
next <- true
|
||||||
|
}
|
||||||
if data, ok := m.Optionv("data").(chan []byte); ok {
|
if data, ok := m.Optionv("data").(chan []byte); ok {
|
||||||
if buf := <-data; len(buf) > 0 {
|
if buf := <-data; len(buf) > 0 {
|
||||||
line += string(buf)
|
line += string(buf)
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
break
|
m.Assert(false)
|
||||||
|
}
|
||||||
|
line = lex.Result(1)
|
||||||
|
|
||||||
|
lex = m.Sesss("lex", "lex").Cmd("scan", line, yac.name(s))
|
||||||
|
|
||||||
|
if lex.Result(0) == "-1" { //加载数据
|
||||||
|
if next, ok := m.Optionv("next").(chan bool); ok {
|
||||||
|
next <- true
|
||||||
|
}
|
||||||
|
if data, ok := m.Optionv("data").(chan []byte); ok {
|
||||||
|
if buf := <-data; len(buf) > 0 {
|
||||||
|
line += string(buf)
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
}
|
||||||
|
m.Assert(false)
|
||||||
}
|
}
|
||||||
|
|
||||||
c := byte(lex.Resulti(0))
|
c := byte(lex.Resulti(0))
|
||||||
state := yac.mat[s][c]
|
state := yac.mat[s][c]
|
||||||
|
|
||||||
if state != nil { //全局语法检查
|
if state != nil { //全局语法检查
|
||||||
line, word = lex.Result(1), append(word, lex.Result(2))
|
if key := m.Sesss("lex").Cmd("parse", line, "key"); key.Resulti(0) == 0 || len(key.Result(2)) <= len(lex.Result(2)) {
|
||||||
// if key := m.Find("lex").Cmd("parse", line, "key"); key.Resulti(0) == 0 || len(key.Result(2)) <= len(lex.Result(2)) {
|
line, word = lex.Result(1), append(word, lex.Result(2))
|
||||||
// } else {
|
} else {
|
||||||
// state = nil
|
state = nil
|
||||||
// }
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if state == nil { //嵌套语法递归解析
|
if state == nil { //嵌套语法递归解析
|
||||||
@ -321,10 +341,11 @@ func (yac *YAC) scan(m *ctx.Message, page int, void int, line string) (string, [
|
|||||||
msg := m.Spawn().Add("detail", yac.hand[hash], word...)
|
msg := m.Spawn().Add("detail", yac.hand[hash], word...)
|
||||||
if m.Back(msg); msg.Hand {
|
if m.Back(msg); msg.Hand {
|
||||||
word = msg.Meta["result"]
|
word = msg.Meta["result"]
|
||||||
|
m.Assert(!msg.Has("return"))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
m.Log("fuck", nil, "return--%s-----%v", line, word)
|
m.Optioni("level2", level)
|
||||||
return line, word
|
return line, word
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -506,18 +527,58 @@ var Index = &ctx.Context{Name: "yac", Help: "语法中心",
|
|||||||
if yac, ok := m.Target().Server.(*YAC); m.Assert(ok) { // {{{
|
if yac, ok := m.Target().Server.(*YAC); m.Assert(ok) { // {{{
|
||||||
m.Optioni("page", yac.page["line"])
|
m.Optioni("page", yac.page["line"])
|
||||||
m.Optioni("void", yac.page["void"])
|
m.Optioni("void", yac.page["void"])
|
||||||
|
m.Options("scan_end", false)
|
||||||
|
m.Option("level2", "1")
|
||||||
|
|
||||||
data := make(chan []byte)
|
data := make(chan []byte)
|
||||||
|
next := make(chan bool, 1)
|
||||||
|
m.Optionv("next", next)
|
||||||
|
end := make(chan bool, 1)
|
||||||
|
var out io.Writer
|
||||||
m.Find("nfs").Call(func(nfs *ctx.Message) *ctx.Message {
|
m.Find("nfs").Call(func(nfs *ctx.Message) *ctx.Message {
|
||||||
buf := nfs.Appendv(nfs.Result(0)).([]byte)
|
o := nfs.Optionv("out")
|
||||||
data <- buf
|
if o != nil {
|
||||||
|
out = o.(io.Writer)
|
||||||
|
}
|
||||||
|
|
||||||
|
buf := []byte{}
|
||||||
|
switch v := nfs.Appendv(nfs.Result(0)).(type) {
|
||||||
|
case []byte:
|
||||||
|
buf = v
|
||||||
|
case string:
|
||||||
|
buf = []byte(v)
|
||||||
|
}
|
||||||
|
select {
|
||||||
|
case data <- buf:
|
||||||
|
<-next
|
||||||
|
case <-end:
|
||||||
|
}
|
||||||
return nil
|
return nil
|
||||||
}, "scan_file", arg[0], "脚本解析")
|
}, "scan_file", arg[0], "脚本解析")
|
||||||
|
|
||||||
go func() {
|
go func() {
|
||||||
|
defer func() {
|
||||||
|
if e := recover(); e != nil {
|
||||||
|
end <- true
|
||||||
|
m.Option("scan_end", true)
|
||||||
|
m.Back(m.Spawn().Add("detail", "scan_end"))
|
||||||
|
}
|
||||||
|
}()
|
||||||
m.Optionv("data", data)
|
m.Optionv("data", data)
|
||||||
line, word := yac.scan(m, m.Optioni("page"), m.Optioni("void"), "")
|
m.Optionv("next", next)
|
||||||
m.Log("fuck", nil, "----%s---%v", line, word)
|
line := ""
|
||||||
|
word := []string{}
|
||||||
|
for {
|
||||||
|
line, word = yac.scan(m, m.Optioni("page"), m.Optioni("void"), line)
|
||||||
|
if out != nil {
|
||||||
|
for i, v := range word {
|
||||||
|
if i == len(word)-1 {
|
||||||
|
break
|
||||||
|
}
|
||||||
|
fmt.Fprintf(out, "%s", v)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
}()
|
}()
|
||||||
}
|
}
|
||||||
// }}}
|
// }}}
|
||||||
|
Loading…
x
Reference in New Issue
Block a user