1

I am trying to run mplayer in slave mode, and control it in GO. Named pipe is used to get position, seek, etc. For some reason with echo command it works, writing in go fails.

package main

import (
    "os"
    "fmt"
    "time"
    "syscall"
    "bufio"
    "os/exec"
    . "csystem"
)

func main() {
    namedpipe := "pipe"
    syscall.Mkfifo(namedpipe, 0666)
    player := "/usr/bin/mplayer";
    playfile := os.Args[1]
    cmd := exec.Command(player,"-vo","null","-slave","-quiet",
            "-input","file="+namedpipe,playfile)
    stdout,_ := cmd.StdoutPipe()
    cmd.Start()
    go func () {
        // file, err := os.OpenFile(namedpipe, os.O_RDWR, os.ModeNamedPipe)
        file, err := os.OpenFile(namedpipe, os.O_RDWR|os.O_CREATE|os.O_APPEND, 0777)
        if err != nil {
            fmt.Println(err)
            return
        }
        fmt.Println("pipe is open")
        defer file.Close()
        w := bufio.NewWriter(file)
        optionA := false
        optionB := true
        for ;; {
            time.Sleep(time.Second)
            if optionA {
                System("echo \"get_time_pos\" > "+namedpipe)
            }
            if optionB {
                n,err := w.Write([]byte("get_time_pos\n"))
                if err != nil {
                    fmt.Println(err)
                    return
                } else {
                    fmt.Println("write pipe ",n)
                }
            }
        }
    } ()
    defer cmd.Wait()
    scanner := bufio.NewScanner(stdout)
    for scanner.Scan() {
        text := scanner.Text()
        fmt.Println(text)
    }
}

optionA: I get stdout output, and echo command give me response ANS_TIME_POSITION=0.9

./mplayergo file.flac
pipe is open
MPlayer 1.3.0 (Debian), built with gcc-9 (C) 2000-2016 MPlayer Team

Playing file.flac.
libavformat version 58.29.100 (external)
Audio only file format detected.
==========================================================================
Opening audio decoder: [ffmpeg] FFmpeg/libavcodec audio decoders
libavcodec version 58.54.100 (external)
AUDIO: 192000 Hz, 2 ch, s32le, 5497.4 kbit/44.74% (ratio: 687172->1536000)
Selected audio codec: [ffflac] afm: ffmpeg (FFmpeg FLAC audio)
==========================================================================
AO: [pulse] 192000Hz 2ch s32le (4 bytes per sample)
Video: no video
Starting playback...
ANS_TIME_POSITION=0.9
ANS_TIME_POSITION=1.8

option B: No errors occurs, pipe is open and writes successfully processed but no response.

./mplayergo file.flac
pipe is open
MPlayer 1.3.0 (Debian), built with gcc-9 (C) 2000-2016 MPlayer Team

Playing file.flac.
libavformat version 58.29.100 (external)
Audio only file format detected.
==========================================================================
Opening audio decoder: [ffmpeg] FFmpeg/libavcodec audio decoders
libavcodec version 58.54.100 (external)
AUDIO: 192000 Hz, 2 ch, s32le, 5497.4 kbit/44.74% (ratio: 687172->1536000)
Selected audio codec: [ffflac] afm: ffmpeg (FFmpeg FLAC audio)
==========================================================================
AO: [pulse] 192000Hz 2ch s32le (4 bytes per sample)
Video: no video
Starting playback...
write pipe  13
write pipe  13

Why does option B not work? What am I missing?

Jonathan Hall
  • 75,165
  • 16
  • 143
  • 189
Rolas
  • 133
  • 8
  • 2
    `w := bufio.NewWriter(file)` creates a buffered writer and `w.Write([]byte("get_time_pos\n"))` might not get flushed to `file`. If you really need the bufio.Writer (for what? why buffer?) you'll have to Flush it after Write. – Volker Dec 01 '20 at 07:05
  • w.Flush() is missing after write! @Volker Thank you! – Rolas Dec 01 '20 at 07:23
  • On a side note: you do not need `;;` in `for { ... }` ;-) – kostix Dec 01 '20 at 08:43

1 Answers1

0

Comment by @Volker solves the issue. w.Flush() is missing after write.

I don't need buffer, so

io.WriteString(file,"get_time_pos\n") 

is better solution.

Rolas
  • 133
  • 8