def completion_mask(editing_dir, editing_file, editing, sqort, dqort, last_sqort, last_dqort, add_space, reg)

#message("editing (%s) editing_dir (%s) editing_file (%s)", editing, editing_dir, editing_file)

    reg = Regexp.new(reg)

    if editing_dir != ""
        if editing_dir[0] == "$"[0]
            i = 1
            env_name = ""
    
            while editing_dir[i] != "/"[0]
                env_name = env_name +  editing_dir[i].chr
                i = i + 1
            end
            
            editing_dir = ENV[env_name] + editing_dir[i..editing_dir.size]
        elsif editing_dir[0] == "~"[0]
            editing_dir = ENV['HOME'] + editing_dir[1..editing_dir.size]
        end
    
        begin
            array = []
    
            Dir.foreach(editing_dir) { |file|
                if file != "." && file != ".."
                    if File.exist?(editing_dir + file) && File.stat(editing_dir + file).directory?
                        file = file + "/"
                    end
    
                    if reg.match(file)
                        #file = editing_dir + file
                        array.push(file)
                    end
                end
            }
    
            array.sort!
            completion(array, editing_file, sqort, dqort, last_sqort, last_dqort, add_space)
            
        rescue SystemCallError
            message("SystemCallError")        
        end
    else
        if editing[0] == '$'[0]
            array = []
            ENV.each {|key, value|
                if File.exist?(value) && File.stat(value).directory? 
                    array.push("$" + key + "/")
                else
                    array.push("$" + key)
                end
            }

            completion(array, editing, sqort, dqort, last_sqort, last_dqort, add_space)
        elsif editing[0] == '~'[0]
            array = ["~/"]

            completion(array, editing, sqort, dqort, last_sqort, last_dqort, add_space)

        else
            begin
               array = [] 
               Dir.foreach(adir_path2()) {|file|
                   path = adir_path2() + file
                   if File.exist?(path) && File.stat(path).directory?
                      file = file + "/"
                   end

                   if file != "./" && file != "../" && reg.match(file)
                       array.push(file)
                   end
                }

                array.sort!
                completion(array, editing, sqort, dqort, last_sqort, last_dqort, add_space)

            rescue SystemCallError
                message("SystemCallError")
            end
        end
    end

    return nil
end

def completion_hook(editing, editing_dir, editing_file, editing_before, earray, cmd, editing_position, sqort, dqort, last_sqort, last_dqort)

#message("cmd (%s) %d editing_before (%s) editing (%s) editing_dir (%s) editing_file (%s)", cmd, editing_position, editing_before, editing, editing_dir, editing_file)

    user_names = ["daisuke", "naohiro", "kensuke"]
    host_names = ["hogehoge.ac.jp", "hogehoge.net"]


    ### ls #############################################################
    if cmd == "ls" 
        if editing.size>=1 && editing[0] == "-"[0]
            array = [
                ["-1", "single column output" ], 
                ["-A", "list all except . and .." ],
                ["-B", "don't list entries ending with ~"],
                ["-C", "list entries in columns sorted vertically"],
                ["-D", "generate output designed for Emacs' dired mode"],
                ["-F", "append file type indicators"],
                ["-G", "inhibit display of group information"],
                ["-H", "sizes in human readable form; powers of 1000"],
                ["-I", "don't list entire matching pattern"],
                ["-L", "list referenced file for sym link"],
                ["-N", "print raw characters"],
                ["-Q", "quote names"],
                ["-R", "list subdirectories recursively"],
                ["-S", "sort by size"],
                ["-T", "specify tab size"],
                ["-U", "unsorted"],
                ["-X", "sort by extension"],
                ["-a", "list entries starting with ."],
                ["-b", "print octal escapes for control characters"],
                ["-c", "status change time"],
                ["-d", "list directory entries instead of contents"],
                ["-f", "unsorted, all, short list"],
                ["-g", "long listing but without owner information"],
                ["-h", "print sizes in human readable form"],
                ["-i", "print file inode numbers"],
                ["-k", "use block size of 1k"],
                ["-l", "long listing"],
                ["-m", "comma separated"],
                ["-n", "numeric uid, gid"],
                ["-o", "no group, long"],
                ["-p", "append file type indicators except *"],
                ["-q", "hide control chars"],
                ["-r", "reverse sort order"],
                ["-s", "display size of each file in blocks"],
                ["-t", "sort by modification time"],
                ["-u", "access time"],
                ["-v", "sort by version (filename treated numerically)"],
                ["-w", "specify screen width"],
                ["-x", "sort horizontally" ]
            ]
            completion2(array, editing, sqort, dqort, last_sqort, last_dqort, true, 3)

            return 3
        end
        
    ### lpr ############################################################
    elsif cmd == "lpr"
        completion_mask(editing_dir, editing_file, editing, sqort, dqort, last_sqort, last_dqort, true, '.+\.ps|.+/')
        
        return 3
        
    ### dd ############################################################
    elsif cmd == "dd"
        if editing.index("if=")  == 0|| editing.index("of=") == 0
            if editing_dir == ""
                completion_mask(editing_dir, editing_file[editing_file.index("=")+1..editing_file.size], editing[editing.index("=")+1..editing.size], sqort, dqort, last_sqort, last_dqort, true, '.+')
            else
                completion_mask(editing_dir[editing_dir.index("=")+1..editing_dir.size], editing_file, editing[editing.index("=")+1..editing.size], sqort, dqort, last_sqort, last_dqort, true, '.+')
            end

            
            return 3

        elsif editing.index("bs=")==0 || editing.index("cbs=")==0 || editing.index("conv=")==0 || editing.index("count=")==0 || editing.index("files=")==0 || editing.index("ibs=")==0 || editing.index("obs=")==0 || editing.index("seek=")==0
            return 2
        else
            array = [
                ["bs=", "block size"],
                ["cbs=", "conversion buffer size"],
                ["conv=", "specify conversions to apply"],
                ["count=", "number of input blocks to copy"],
                ["files=", "specify number of input files to copy and concatenate"],
                ["ibs=", "input block size"],
                ["if=", "specify input file"],
                ["obs=", "output bloack size"],
                ["of=", "specify output file"],
                ["seek=", "output blocks initially skipped"],
                ["skip=", "input blocks initially skipped"]
            ]

            completion2(array, editing, sqort, dqort, last_sqort, last_dqort, false, 8)
            return 3
        end

    ### du ############################################################
    elsif cmd == "du"
        if editing.size>=1 && editing[0] == "-"[0]
            array = [
                ["-L", "dereference symlinks"],
                ["-a", "write counts for all files"],
                ["-d", "skip directories on different filesystems"],
                ["-k", "use block size of 1k"],
                ["-o", "do not add child directories' usage to parent's total"],
                ["-r", "notify about unreadable files/directories"],
                ["-s", "only display total for each argument"]
            ]
            completion2(array, editing, sqort, dqort, last_sqort, last_dqort, true, 3)
            return 3

        end

    ### find ############################################################
    elsif cmd == "find"
        if editing.size >= 1 && editing[0]=="-"[0]
            array = [
                "-amin", "-empty", "-fstype", "-iregex", "-mtime", "-perm",
                "-type", "-anewer", "-exec", "-gid", "-links", "-name", 
                "-print", "-uid", "-atime", "-false", "-group", "-lname",
                "-newer", "-print0", "-used", "-cmin", "-fls", "-help", "-ls",
                "-nogroup", "-printf", "-user", "-cnewer", "-follow",
                "-ilname", "-maxdepth", "-noleaf", "-prune", "-version",
                "-ctime", "-fprint", "-iname", "-mindepth", "-nouser", 
                "-regex", "-xdev", "-daystart", "-fprint0", "-inum", "-mmin",
                "-ok", "-size", "-xtype", "-depth", "-fprintf", "-ipath",
                "-mount", "-path", "-true"
            ]

            completion(array, editing, sqort, dqort, last_sqort, last_dqort, true)
            return 3
        end

    ### sed ############################################################
    elsif cmd == "sed"
        if editing.size >= 1 && editing[0]=="-"[0]
            array = [
                ["-e", "add sed commands to run"],
                ["-f", "add contents of file to commands to run"],
                ["-n", "suppress automatic printing of pattern space"]
            ]

            completion2(array, editing, sqort, dqort, last_sqort, last_dqort, true, 5)
            return 3
        end

    ### printenv ############################################################
    elsif cmd == "printenv"
        array = []

        ENV.each_key {|key|
            array.push(key)
        }

        completion(array, editing_file, sqort, dqort, last_sqort, last_dqort, true)
        return 3

    ### xargs ############################################################
    elsif cmd == "xargs"
        if editing.size >= 1 && editing[0]=="-"[0]
            array = [
                ["-p", "prompt user for each command"],
                ["-t", "verbose - echo each command"],
                ["-x", "exit if max size exceeded"],
                ["-E", ""],
                ["-I", ""],
                ["-L", ""],
                ["-e", ""],
                ["-i", ""],
                ["-l", ""],
                ["-n", ""],
                ["-s", ""]
            ]

            completion2(array, editing, sqort, dqort, last_sqort, last_dqort, true, 5)
            return 3

        elsif editing_position == 1
            return 1

        else
            return 0
        end

    ### sudo ############################################################
    elsif cmd == "sudo"
        earray.each { |str|
            if str == "-a" || str == "-c" || str == "-p" || str == "-u" || str == "-e"
                editing_position = editing_position -1
            end
        }

        if editing.size >= 1 && editing[0]=="-"[0]
            array = [
                ["-H", "set HOME environment variable"],
                ["-K", "remove user timestamp"],
                ["-L", "list options from Default section"],
                ["-S", "read password from stdin"],
                ["-V", "show version"],
                ["-b", "run command in backgroud"],
                ["-h", "show help"],
                ["-k", "invalidate user timestamp"],
                ["-l", "list allowed commands"],
                ["-p", "password prompt"],
                ["-r", "Kerberos realm"],
                ["-s", "run SHELL"],
                ["-u", "user name"],
                ["-v", "validate user timestamp"]
            ]

            completion2(array, editing, sqort, dqort, last_sqort, last_dqort, true, 3)
            return 3

        elsif editing_before == "-u"
            array = user_names
            completion(array, editing, sqort, dqort, last_sqort, last_dqort, true)
            return 3

        elsif editing_position == 1
            return 1

        else
            return 0
        end

    ### screen ############################################################
    elsif cmd == "screen"
        if editing.size >= 1 && editing[0]=="-"[0]
            array = [
                ["-A", "adapt all windows to the new display width & height"],
                ["-D", "detach and logout remote (with -r: reattach here)"],
                ["-L", "terminal's last character can be safely updated"],
                ["-O", "choose optimal output rather than exact vt100 emulation"],
                ["-R", "reattach if possible, otherwise start a new session"],
                ["-S", "name this session <pid>.sockname instead of <pid>.<tty>.<host>"],
                ["-T", "use term as $TERM for windows, rather than \"screen\""],
                ["-U", "tell screen to use UTF-8 encoding"],
                ["-X", "execute command as a screen command in the specified session"],
                ["-a", "force all capabilities into each window's termcap"],
                ["-c", "read configuration file instead of '.screenrc'"],
                ["-d", "detach the elsewhere running screen (with -r: reattach here)"],
                ["-dmS", "start as daemon, screen session in detached mode"],
                ["-e", "change command characters"],
                ["-f", "set flow control"],
                ["-h", "set the size of the scrollback history buffer"],
                ["-i", "interrupt output sooner when flow control is on"],
                ["-l", "login mode on (update utmp database)"],
                ["-ls", "list sessions/socket directory"],
                ["-ln", "login mode off (do not update utmp database)"],
                ["-m", "ignore $STY variable, do create a new screen session"],
                ["-p", "preselect the named window"],
                ["-q", "quiet startup, exit with non-zero return code if unsuccessful"],
                ["-r", "reattach to a detached screen process"],
                ["-s", "shell to execute rather than $SHELL"],
                ["-t", "set title (window's name)"],
                ["-v", "print screen version"],
                ["-wipe", "do nothing, clean up SockDir"],
                ["-x", "attach to a not detached screen (multi display mode)"]
            ]

            completion2(array, editing, sqort, dqort, last_sqort, last_dqort, true, 5)
            return 3

        elsif editing_before == "-r"
            array = []

            `screen -ls`.each {|line|
                words = line.split

                if words.size == 2 && words[1] == "(Detached)"
                    array.push(words[0])
                end
            }

            completion(array, editing, sqort, dqort, last_sqort, last_dqort, true)
            return 3
       end

    ### mount ############################################################
    elsif cmd == "mount"
        earray.each { |str|
            if str == "-F" || str == "-o" || str == "-t"
                editing_position = editing_position -1
            end
        }

        if editing.size >= 1 && editing[0]=="-"[0]
            array = [
                ["-a", "mount all filesystems in fstab"],
                ["-d", "cause everything to be done except for the actual system call"],
                ["-f", "forced mount"],
                ["-o", "specify file system options"],
                ["-p", "print mounted file systems"],
                ["-r", "mount readonly"],
                ["-t", "specify file system type"],
                ["-u", "change status of already mounted filesystem"],
                ["-v", "verbose mode"],
                ["-w", "mount read/write"]
            ]

            completion2(array, editing, sqort, dqort, last_sqort, last_dqort, true, 5)
            return 3

        elsif editing_before == "-o"
            array = [
                ["current", "use current options on already mounted file system"],
                ["dev", "interpret devices"],
                ["dirty", "allow mount even if not cleanly unmounted"],
                ["exec", "permit execution of binaries"],
                ["force", "force R/W mount of unclean filesystem"],
                ["fstab", "use options listed in /etc/fstab"],
                ["grpid", "new file gets group ID of directory"],
                ["noasync", "do I/O synchronously"],
                ["sync", "do I/O synchronously"],
                ["noatime", "don't update access time"],
                ["noauto", "can only be mounted explicitly"],
                ["noclusterr", "disable read clustering"],
                ["noclusterw", "disable write clustering"],
                ["nodev", "don't interpret devices"],
                ["noexec", "don't allow execution of binaries"],
                ["nogrpid", "new file gets fsgid of current process"],
                ["nosuid", "ignore suid and sgid bits"],
                ["nosymfollow", "don't follow symlinks"],
                ["async", "do all I/O asynchronously"],
                ["nosync", "do all I/O asynchronously"],
                ["rdonly", "mount file system read-only"],
                ["suid", "use suid and sgib bits"],
                ["suiddir", "allow suid bits on directories"],
                ["sync", "do all I/O synchronously"],
                ["union", "cause the namespace at the mount point to appear as the"],
                ["update", "change status of already mounted filesystem"]
            ]

            completion2(array, editing, sqort, dqort, last_sqort, last_dqort, true, 15)
            return 3

        elsif editing_before == "-t"
            os = `uname -s`

            if os == "FreeBSD"
                array = [
                    "cd9660", "devfs", "ext2fs", "fdesc", "kernfs",
                    "linprocfs",
                    "mfs", "msdos", "nfs", "ntfs", "null", "nwfs", "protal",
                    "procfs", "std", "udf", "ufs", "umap", "union"
                ]
            else    # Linux 
                array = [
                    "autofs", "bdev", "cramfs", "devpts", "ext2", "ext3",
                    "nfs", "pipefs", "proc", 
                    "ramfs", "reiserfs", "rootfs", "shm", "sockfs", "tmpfs",
                    "usbdevfs", "usbfs"
                ]
            end

            completion(array, editing, sqort, dqort, last_sqort, last_dqort, true)
            
            return 3


        elsif editing_position == 1
            array = []

            `cat /etc/fstab`.each {|line|
                a = line.split

                if a.size == 6
                    array.push(a[0])
                    array.push(a[1])
                end
            }

            array.uniq!
            array.sort!

            completion(array, editing, sqort, dqort, last_sqort, last_dqort, true)
            
            return 3
        end
        
    ### diff ############################################################
    elsif cmd == "diff"
        if editing.size >= 2 && editing[0]=="-"[0] && editing[1]=="-"[0]
            array = [
                ["--brief", "output only whether files differ"],
                ["--changed-group-format", "set changed group format"],
                ["--context", "output a context diff"],
                ["--ed", "output an ed script"],
                ["--exclude", "exclude files matching pattern"],
                ["--exclude-from", "exclude files matching pattern in file"],
                ["--expand-tabs", "expand tabs to spaces"],
                ["--forward-ed", "output a reversed ed script"],
                ["--from-file", "compare specified file to all operands"],
                ["--help", "display help info"],
                ["--horizon-lines", "set number of lines to keep in prefix and suffix"],
                ["--ifdef", "output merged file with preprocessor directives"],
                ["--ignore-all-space", "ignore all white space"],
                ["--ignore-blank-lines", "ignore lines that are all blank"],
                ["--ignore-case", "case insensitive"],
                ["--ignore-file-name-case", "ignore case when comparing file names"],
                ["--ignore-matching-lines", "ignore lines that match regex"],
                ["--ignore-space-change", "ignore changes in the amount of white space"],
                ["--ignore-tab-expansion", "ignore changes due to tab expansion"],
                ["--initial-tab", "prepend a tab"],
                ["--label", "set label to use instead of file name"],
                ["--left-column", "output only left column of common lines"],
                ["--line-format", "set line format"],
                ["--minimal", "try to find a smaller set of changes"],
                ["--new-file", "treat absent files as empty"],
                ["--new-group-format", "set new group format"],
                ["--new-line-format", "set new line format"],
                ["--no-ignore-file-name-case", "consider case when comparing file names"],
                ["--normal", "output a normal diff"],
                ["--old-group-format", "set old group format"],
                ["--old-line-format", "set old line format"],
                ["--ignore-all-space", "ignore all white space"],
                ["--ignore-blank-lines", "ignore lines that are all blank"],
                ["--ignore-case", "case insensitive"],
                ["--ignore-file-name-case", "ignore case when comparing file names"],
                ["--ignore-matching-lines", "ignore lines that match regex"],
                ["--ignore-space-change", "ignore changes in the amount of white space"],
                ["--ignore-tab-expansion", "ignore changes due to tab expansion"],
                ["--initial-tab", "prepend a tab"],
                ["--label", "set label to use instead of file name"],
                ["--left-column", "output only left column of common lines"],
                ["--line-format", "set line format"],
                ["--minimal", "try to find a smaller set of changes"],
                ["--new-file", "treat absent files as empty"],
                ["--new-group-format", "set new group format"],
                ["--new-line-format", "set new line format"],
                ["--no-ignore-file-name-case", "consider case when comparing file names"],
                ["--normal", "output a normal diff"],
                ["--old-group-format", "set old group format"],
                ["--old-line-format", "set old line format"],
                ["--paginate", "output through pr"],
                ["--rcs", "RCS format diff"],
                ["--recursive", "recursively compare subdirectories"],
                ["--report-identical-files", "report when two files are the same"],
                ["--show-c-function", "show C function of each change"],
                ["--show-function-line", "show the most recent line matching regex"],
                ["--side-by-side", "output in two columns"],
                ["--speed-large-files", "assume large files and many small changes"],
                ["--starting-file", "set first file in comparison"],
                ["--strip-trailing-cr", "strip trailing carriage return on input"],
                ["--suppress-common-lines", "do not output common lines"],
                ["--tabsize", "specify width of tab"],
                ["--text", "treat all files as text"],
                ["--to-file", "compare all operands to specified file"],
                ["--unchanged-group-format", "set unchanged group format"],
                ["--unchanged-line-format", "set unchanged line format"],
                ["--unidirectional-new-file", "treat absent first files as empty"],
                ["--unified", "output a unified diff"],
                ["--version", "display version info"],
                ["--width", "set size of line"]
            ]

            completion2(array, editing, sqort, dqort, last_sqort, last_dqort, true, 26)
            return 3

        elsif editing.size >= 1 && editing[0]=="-"[0]
            array = [
                ["-B", "ignore lines that are all blank"],
                ["-C", "output a context diff"],
                ["-D", "output merged file with preprocessor directives"],
                ["-E", "ignore changes due to tab expansion"],
                ["-F", "show the most recent line matching regex"],
                ["-H", "assume large files and many small changes"],
                ["-I", "ignore lines that match regex"],
                ["-L", "set label to use instead of file name"],
                ["-N", "treat absent files as empty"],
                ["-P", "treat absent first files as empty"],
                ["-S", "set first file in comparison"],
                ["-T", "prepend a tab"],
                ["-U", "output a unified diff"],
                ["-W", "set size of line"],
                ["-X", "exclude files matching pattern in file"],
                ["-a", "treat all files as text"],
                ["-b", "ignore changes in the amount of white space"],
                ["-d", "try to find a smaller set of changes"],
                ["-e", "output an ed script"],
                ["-f", "output a reversed ed script"],
                ["-i", "case insensitive"],
                ["-l", "output through pr"],
                ["-n", "RCS format diff"],
                ["-p", "show C function of each change"],
                ["-q", "output only whether files differ"],
                ["-r", "recursively compare subdirectories"],
                ["-s", "report when two files are the same"],
                ["-t", "expand tabs to spaces"],
                ["-v", "display version info"],
                ["-w", "ignore all white space"],
                ["-x", "exclude files matching pattern"],
                ["-y", "output in two columns"]
            ]

            completion2(array, editing, sqort, dqort, last_sqort, last_dqort, true, 5)
            return 3
        end

    ### gzip ############################################################
    elsif cmd == "gzip"
        if editing.size >= 2 && editing[0]=="-"[0] && editing[1]=="-"[0]
            array = [
                ["--force", "force overwrite"],
                ["--help", "display help message"],
                ["--license", "display software license"],
                ["--list", "list compressed file contents"],
                ["--name", "save or restore the original name and time stamp"],
                ["--no-name", "do not save or restore the original name andi time stamp"],
                ["--revursive", "operate recursively on directories"],
                ["--silent", "suppress all warnings"],
                ["--suffix", "specify suffix for compressed files"],
                ["--test", "test compressed file integrity"],
                ["--to-stdout", "write on standard output"],
                ["--uncompress", "decompress"],
                ["--verbose", "verbose mode"],
                ["--version", "display version number"],
                ["--best", "fast"]
            ]

            completion2(array, editing, sqort, dqort, last_sqort, last_dqort, true, 14)
            return 3

        elsif editing.size >= 1 && editing[0]=="-"[0]
            array = [
                ["-f", "force overwrite"],
                ["-L", "display software license"],
                ["-N", "save or restore the original name and time stamp"],
                ["-S", "specify suffix for compressed files"],
                ["-V", "display version number"],
                ["-c", "write on standard output"],
                ["-d", "decompress"],
                ["-h", "display help message"],
                ["-l", "list compressed file contents"],
                ["-n", "do not save or restore the original name and time stamp"],
                ["-q", "suppress all warnings"],
                ["-r", "operate recursively on directories"],
                ["-t", "test compressed file integrity"],
                ["-v", "verbose mode"],
                ["-1", ""],
                ["-2", ""],
                ["-3", ""],
                ["-4", ""],
                ["-5", ""],
                ["-6", ""],
                ["-7", ""],
                ["-8", ""],
                ["-9", ""]
            ]

            completion2(array, editing, sqort, dqort, last_sqort, last_dqort, true, 5)
            return 3
        else
            option_d = false
            earray.each { |str|
                if str == "-d"
                    option_d = true
                end
            }

            if option_d
                completion_mask(editing_dir, editing_file, editing, sqort, dqort, last_sqort, last_dqort, true, '.+\.gz|.+/')
                return 3
            end
        end

    ### bzip2 ############################################################
    elsif cmd == "bzip2"
        if editing.size >= 2 && editing[0]=="-"[0] && editing[1]=="-"[0]
            array = [
                ["--compress", "compress"],
                ["--decompress", "decompress"],
                ["--force", "force overwrite"],
                ["--help", "display help message"],
                ["--keep", "keep (don't delete) input files"],
                ["--license", "display software license"],
                ["--quiet", "suppress all warnings"],
                ["--stdout", "write on standard output"],
                ["--test", "test compressed file integrity"],
                ["--verbose", "verbose mode"],
                ["--version", "display version number"]
            ]

            completion2(array, editing, sqort, dqort, last_sqort, last_dqort, true, 14)
            return 3

        elsif editing.size >= 1 && editing[0]=="-"[0]
            array = [
                ["-L", "display software license"],
                ["-V", "display version number"],
                ["-c", "write on standard output"],
                ["-d", "decompress"],
                ["-f", "force overwrite"],
                ["-h", "display help message"],
                ["-k", "keep (don't delete) input files"],
                ["-q", "suppress all warnings"],
                ["-s", "use less memory (at most 2500k)"],
                ["-t", "test compressed file integrity"],
                ["-v", "verbose mode"],
                ["-z", "compress"],
                ["-1", ""],
                ["-2", ""],
                ["-3", ""],
                ["-4", ""],
                ["-5", ""],
                ["-6", ""],
                ["-7", ""],
                ["-8", ""],
                ["-9", ""]
            ]

            completion2(array, editing, sqort, dqort, last_sqort, last_dqort, true, 5)
            return 3
        else
            option_d = false
            earray.each { |str|
                if str == "-d"
                    option_d = true
                end
            }

            if option_d
                completion_mask(editing_dir, editing_file, editing, sqort, dqort, last_sqort, last_dqort, true, '.+\.bz2|.+/')
                return 3
            end
        end

    ### perl ############################################################
    elsif cmd == "perl"
        if editing.size >= 1 && editing[0]=="-"[0]
            array = [
                ["-I", "specify @INC/#include directory (may be used more than once)"],
                ["-M", "module.. executes `use/no module...' before executing your script."],
                ["-P", "run script through C preprocessor before compilation"],
                ["-S", "look for the script using PATH environment variable"],
                ["-T", "turn on tainted checks"],
                ["-U", "allow unsafe operations"],
                ["-V", "print perl configuration information"],
                ["-a", "autosplit mode with -n or -p (splits $_ into @F)"],
                ["-c", "check syntax only (runs BEGIN and END blocks)"],
                ["-d", "run scripts under debugger"],
                ["-d:", "run under control of a debugging/tracing module"],
                ["-h", "list help summary"],
                ["-i", "edit <> files in place (make backup if extension supplied)"],
                ["-l", "enable line ending processing, specifies line terminator"],
                ["-n", "assume 'while (<>) { ... }' loop around your script"],
                ["-p", "assume loop like -n but print line also like sed"],
                ["-s", "enable some switch parsing for switches after script name"],
                ["-u", "dump core after parsing script"],
                ["-v", "print version number, patchlevel plus VERY IMPORTANT perl info"],
                ["-w", "TURN WARNINGS ON FOR COMPILATION OF YOUR SCRIPT. Recommended."],
                ["-x", "strip off text before #!perl line and perhaps cd to directory"],
                ["-0", ""],
                ["-D", ""],
                ["-F", ""],
                ["-e", ""]
            ]

            completion2(array, editing, sqort, dqort, last_sqort, last_dqort, true, 5)
            return 3
        end

    ### python ############################################################
    elsif cmd == "python"
        if editing.size >= 1 && editing[0]=="-"[0]
            array = [
                ["-E", "ignore environment variables (such as PYTHONPATH)"],
                ["-O", "optimize generated bytecode"],
                ["-OO", "remove doc-strings in addition to the -O optimizations"],
                ["-Q", "division options"],
                ["-S", "don't imply 'import site' on initialization"],
                ["-V", "display version information"],
                ["-W", "warning control"],
                ["-c", "program passed in as string (terminates option list)"],
                ["-d", "debug output from parser"],
                ["-h", "display help information"],
                ["-i", "inspect interactively after running script"],
                ["-m", "run library module as a script (terminates option list)"],
                ["-t", "issue warnings about inconsistent tab usage"],
                ["-tt", "issue errors about inconsistent tab usage"],
                ["-u", "unbuffered binary stdout and stderr"],
                ["-v", "verbose (trace import statements)"],
                ["-x", "skip first line of source, allowing use of non-Unix forms of #!cmd"]
            ]

            completion2(array, editing, sqort, dqort, last_sqort, last_dqort, true, 5)
            return 3
        end

    ### ruby ############################################################
    elsif cmd == "ruby"
        if editing.size >= 2 && editing[0]=="-"[0] && editing[1]=="-"[0]
            array = [
                ["--copyright", "print the copyright"],
                ["--debug", "set debugging flags (set $DEBUG to true)"],
                ["--help", "print help message"],
                ["--verbose", "print version number, then turn on verbose mode"],
                ["--version",  "print the version"],
                ["--yydebug", "enable yacc debugging in the parser"]
            ]

            completion2(array, editing, sqort, dqort, last_sqort, last_dqort, true, 22)
            return 3

        elsif editing.size >= 1 && editing[0]=="-"[0]
            array = [
                ["-0",  "specify record separator"],
                ["-C",  "cd to directory, before executing your script"],
                ["-F",  "split() pattern for autosplit (-a)"],
                ["-I",  "specify $LOAD_PATH directory (may be used more than once)"],
                ["-K",  "specifies KANJI (Japanese) code-set"],
                ["-S",  "look for the script using PATH environment variable"],
                ["-T",  "turn on tainting checks"],
                ["-W",  "set warning level"],
                ["-a",  "autosplit mode with -n or -p (splits $_ into $F)"],
                ["-c",  "check syntax only"],
                ["-e",  "one line of script (several -e's allowed, omit program fil"],
                ["-i",  "edit ARGV files in place (make backup if extension supplie"],
                ["-n",  "l  -- assume 'while gets(); ... end' loop around your script"],
                ["-p",  "assume loop like -n but print line also like sed"],
                ["-r",  "require the library, before executing your script"],
                ["-s",  "enable some switch parsing for switches after script name"],
                ["-w",  "turn warnings on for your script"],
                ["-x",  "strip off text before #!ruby line and perhaps cd to direct"]
            ]

            completion2(array, editing, sqort, dqort, last_sqort, last_dqort, true, 5)
            return 3
        end

    ### less ############################################################
    elsif cmd == "less"
        if editing.size >= 2 && editing[0]=="-"[0] && editing[1]=="-"[0]
            array = [
                ["--CLEAR-SCREEN", "clear screen before repaints"],
                ["--HILITE-SEARCH", "disable highlighting of search matches"],
                ["--HILITE-UNREAD", "highlight first unread line after forward m"],
                ["--IGNORE-CASE", "ignore case in all searches"],
                ["--LINE-NUMBERS", "show line numbers"],
                ["--LOG-FILE", "copy input to file, overwriting if necessar"],
                ["--LONG-PROMPT", "prompt very verbosely"],
                ["--QUIT-AT-EOF", "exit when end-of-file is reached"],
                ["--RAW-CONTROL-CHARS", "display control chars; keep track of screen"],
                ["--SILENT", "QUIET  -- limit use of bell"],
                ["--UNDERLINE-SPECIAL", "treat backspaces, tabs and carriage returns"],
                ["--auto-buffers", "don't automatically allocate buffers for pi"],
                ["--buffers", "specify amount of buffer space used for eac"],
                ["--chop-long-lines", "truncate long lines instead of folding"],
                ["--clear-screen", "repaint screen instead of scrolling"],
                ["--dumb", "suppress error message if terminal is dumb"],
                ["--force", "force opening of non-reqular files"],
                ["--help", "display summary of less commands"],
                ["--hilite-search", "highlight only one match for searches"],
                ["--hilite-unread", "highlight first unread line after forward p"],
                ["--ignore-case", "ignore case in searches that lack uppercase"],
                ["--jump-target", "specify screen position of target lines"],
                ["--lesskey-file", "use specified lesskey file"],
                ["--line-numbers", "don't keep track of line numbers"],
                ["--log-file", "copy input to file"],
                ["--long-prompt", "prompt verbosely"],
                ["--max-back-scroll", "specify backward scroll limit"],
                ["--max-forw-scroll", "specify forward scroll limit"],
                ["--no-init", "disable use of terminal init string"],
                ["--no-keypad", "disable use of keypad terminal init string"],
                ["--no-lessopen", "ignore the LESSOPEN environment variable"],
                ["--pattern", "start at specified pattern"],
                ["--prompt", "specify prompt format"],
                ["--quit-at-eof", "exit the second time end-of-file is reached"],
                ["--quit-if-one-screen", "exit if entire file fits on first screen"],
                ["--quotes", "change quoting character"],
                ["--raw-control-chars", "display raw control characters"],
                ["--search-skip-screen", "begin forward searches after last displayed"],
                ["--shift", "specify amount to move when scrolling horiz"],
                ["--silent", "quiet  -- never use bell"],
                ["--squeeze-blank-lines", "squeeze consecutive blank lines down to one"],
                ["--status-column", "display status column on the left"],
                ["--tabs", "set tab stops"],
                ["--tag", "edit file containing tag"],
                ["--tag-file", "specify tags file"],
                ["--tilde", "don't display tildes after end of file"],
                ["--underline-special", "send backspaces and carriage returns to the"],
                ["--version", "display version information"],
                ["--window", "specify scrolling window size"]
            ]

            completion2(array, editing, sqort, dqort, last_sqort, last_dqort, true, 22)
            return 3

        elsif editing.size >= 1 && editing[0]=="-"[0]
            array = [
                ["-\"", "change quoting character"],
                ["-#", "specify amount to move when scrolling horizontally"],
                ["-?", "display summary of less commands"],
                ["-B", "don't automatically allocate buffers for pipes"],
                ["-C", "clear screen before repaints"],
                ["-E", "exit when end-of-file is reached"],
                ["-F", "exit if entire file fits on first screen"],
                ["-G", "disable highlighting of search matches"],
                ["-I", "ignore case in all searches"],
                ["-J", "display status column on the left"],
                ["-L", "ignore the LESSOPEN environment variable"],
                ["-M", "prompt very verbosely"],
                ["-N", "show line numbers"],
                ["-O", "copy input to file, overwriting if necessary"],
                ["-P", "specify prompt format"],
                ["-Q", "limit use of bell"],
                ["-R", "display control chars; keep track of screen effects"],
                ["-S", "truncate long lines instead of folding"],
                ["-T", "specify tags file"],
                ["-U", "treat backspaces, tabs and carriage returns as control characters"],
                ["-V", "display version information"],
                ["-W", "highlight first unread line after forward movement"],
                ["-X", "disable use of terminal init string"],
                ["-a", "begin forward searches after last displayed line"],
                ["-b", "specify amount of buffer space used for each file"],
                ["-c", "repaint screen instead of scrolling"],
                ["-d", "suppress error message if terminal is dumb"],
                ["-e", "exit the second time end-of-file is reached"],
                ["-f", "force opening of non-reqular files"],
                ["-g", "highlight only one match for searches"],
                ["-h", "specify backward scroll limit"],
                ["-i", "ignore case in searches that lack uppercase"],
                ["-j", "specify screen position of target lines"],
                ["-k", "use specified lesskey file"],
                ["-m", "prompt verbosely"],
                ["-n", "don't keep track of line numbers"],
                ["-o", "copy input to file"],
                ["-p", "start at specified pattern"],
                ["-q", "never use bell"],
                ["-r", "display raw control characters"],
                ["-s", "squeeze consecutive blank lines down to one"],
                ["-t", "edit file containing tag"],
                ["-u", "send backspaces and carriage returns to the terminal"],
                ["-w", "highlight first unread line after forward page"],
                ["-x", "set tab stops"],
                ["-y", "specify forward scroll limit"],
                ["-z", "specify scrolling window size"],
                ["-~", "don't display tildes after end of file"]
            ]

            completion2(array, editing, sqort, dqort, last_sqort, last_dqort, true, 5)
            return 3
        end

    ### grep ############################################################
    elsif cmd == "grep"
        if editing.size >= 2 && editing[0]=="-"[0] && editing[1]=="-"[0]
            array = [
                ["--after-context", "specify lines of trailing context"],
                ["--basic-regexp", "use basic regular expression"],
                ["--before-context", "specify lines of leading context"],
                ["--binary-files", "specify type to assume for binary files"],
                ["--byte-offset", "print the byte offset with output lines"],
                ["--color", "distinguish matching string"],
                ["--context", "specify lines of context"],
                ["--count", "only print a count of matching lines"],
                ["--devices", "specify handling of devices, FIFOs and socke"],
                ["--directories",  "specify handling of directories"],
                ["--exclude", "skip files matching specified pattern"],
                ["--exclude-from", "skip files matching pattern in specified fil"],
                ["--extended-regexp", "use extended regular expression"],
                ["--file", "specify pattern file"],
                ["--files-with-matches", "output matching files' names only"],
                ["--files-without-match", "output non-matching files' names only"],
                ["--fixed-strings", "use literal strings"],
                ["--help", "display help"],
                ["--ignore-case", "case-insensitive"],
                ["--include", "examine files matching specified pattern"],
                ["--invert-match", "select non-matching lines"],
                ["--label", "provide filename to print for stdin"],
                ["--line-buffered", "flush output on every line"],
                ["--line-number", "prefix output with line numbers"],
                ["--line-regexp", "force pattern to match only whole lines"],
                ["--max-count", "stop after specified no of matches"],
                ["--mmap", "memory map input"],
                ["--no-filename",  "suppress printing of filenames"],
                ["--no-messages", "suppress messages about unreadable"],
                ["--null", "print 0 byte after FILE name"],
                ["--only-matching", "show only matching part of line"],
                ["--perl-regexp", "use perl regular expression"],
                ["--recursive", "recurse subdirectories"],
                ["--regexp", "specify pattern"],
                ["--silent", "suppress normal output"],
                ["--text", "process binary file as if it were text"],
                ["--version", "display version info"],
                ["--with-filename", "print filename with each match"],
                ["--word-regexp", "force pattern to match only whole words"]
            ]

            completion2(array, editing, sqort, dqort, last_sqort, last_dqort, true, 22)
            return 3

        elsif editing.size >= 1 && editing[0]=="-"[0]
            array = [
                ["-A",      "specify lines of trailing context"],
                ["-B",      "specify lines of leading context"],
                ["-C",      "specify lines of context"],
                ["-D",      "specify handling of devices, FIFOs and sockets"],
                ["-E",      "use extended regular expression"],
                ["-F",      "use literal strings"],
                ["-G",      "use basic regular expression"],
                ["-H",      "print filename with each match"],
                ["-I",      "process binary files as if non-matching"],
                ["-L",      "output non-matching files' names only"],
                ["-P",      "use perl regular expression"],
                ["-R",      "recurse subdirectories"],
                ["-V",      "display version info"],
                ["-Z",      "print 0 byte after FILE name"],
                ["-a",      "process binary file as if it were text"],
                ["-b",      "print the byte offset with output lines"],
                ["-c",      "only print a count of matching lines"],
                ["-d",      "specify handling of directories"],
                ["-e",      "specify pattern"],
                ["-f",      "specify pattern file"],
                ["-h",      "suppress printing of filenames"],
                ["-i",      "case-insensitive"],
                ["-l",      "output matching files' names only"],
                ["-m",      "stop after specified no of matches"],
                ["-n",      "prefix output with line numbers"],
                ["-o",      "show only matching part of line"],
                ["-q",      "suppress normal output"],
                ["-s",      "suppress messages about unreadable"],
                ["-v",      "select non-matching lines"],
                ["-w",      "force pattern to match only whole words"],
                ["-x",      "force pattern to match only whole lines"],
                ["-y",      "case-insensitive"]
            ]

            completion2(array, editing, sqort, dqort, last_sqort, last_dqort, true, 5)
            return 3
        end

    ### dir_move ############################################################
    elsif cmd == "dir_move"
        completion_mask(editing_dir, editing_file, editing, sqort, dqort, last_sqort, last_dqort, true, '.+/')
        
        return 3

    ### which whereis ########################################################
    elsif cmd == "which" || cmd == "whereis"
        return 1

    ### kill ############################################################
    elsif cmd == "kill"
        if editing.size>=1 && editing[0] == "-"[0]
            array = [
                ["-l", "list signal names or numbers of specified signals"],
                ["-n", "specify siganl number"],
                ["-s", "specify signal name"],
                ["-ABRT", "Abort. When serious error occur"],
                ["-ALRM", "Alarm."],
                ["-BUS", ""],
                ["-CHLD", ""],
                ["-CONT", ""],
                ["-EMT", ""],
                ["-EXIT", ""],
                ["-FPE", ""],
                ["-HUP", "Hungup. When terminal chnaged to offline or user logouted"],
                ["-ILL", ""],
                ["-INFO", ""],
                ["-INT", "Interrupt. CTRL-C"],
                ["-IO", ""],
                ["-KILL", ""],
                ["-PIPE", ""],
                ["-PROF", ""],
                ["-QUIT", "Quit. CTRL-\\"],
                ["-SEGV", ""],
                ["-STOP", ""],
                ["-SYS", ""],
                ["-TERM", "When system is shutdowning"],
                ["-THR", ""],
                ["-TRAP", ""],
                ["-TSTP", ""],
                ["-TTIN", ""],
                ["-TTOU", ""],
                ["-URG", ""],
                ["-USR1", ""],
                ["-USR2", ""],
                ["-VTALRM", ""],
                ["-WINCH", "when terminal size were changed"],
                ["-XCPU", ""],
                ["-XFSZ", ""]
            ]

            completion2(array, editing, sqort, dqort, last_sqort, last_dqort, true, 8)
            return 3
        elsif editing_before == "-l" || editing_before == "-s"
            array = ["ABRT", "ALRM", "BUS", "CHLD", "CONT", "EMT", "EXIT", "FPE", "HUP", "ILL", "INFO", "INT", "IO", "KILL", "PIPE", "PROF", "QUIT", "SEGV", "STOP", "SYS", "TERM", "THR", "TRAP", "TSTP", "TTIN", "TTOU", "URG", "USR1", "USR2", "VTALRM", "WINCH", "XCPU", "XFSZ"]

            completion(array, editing, sqort, dqort, last_sqort, last_dqort, true)
            return 3
        else
            array = []

            words = -1
            `ps a | grep -v ps | grep -v grep`.each do |line|
                array2 = line.split()

                if words == -1
                    words = array2.size
                else
                    if words == 5 # GNU BSD Solaris ps
                        if array2[0].to_i != 0
                            program = ""
                            i = 4
                            while i < array2.size
                                program << array2[i] + " "
                                i = i + 1
                            end
                            
                            str = sprintf("%-8s%-6s%-11s %s", array2[1], array2[2], array2[3], program)
                            array.push([array2[0], str])
                        end
                    elsif words == 8 # cygwin
                        if array2[0].to_i == 0
                            array2.shift
                        end
                        if array2[0].to_i != 0
                            program = ""
                            i = 7
                            while i < array2.size
                                program << array2[i] + " "
                                i = i + 1
                            end

                            str = sprintf("%s", program)

                            array.push([array2[0], str])
                        end
                    end
                end
            end

            array.uniq!
            array.sort!

            completion2(array, editing, sqort, dqort, last_sqort, last_dqort, true, 10)
        
            return 3
        end

    ### chmod ############################################################
    elsif cmd == "chmod"
        if editing.size>=1 && editing[0] == "-"[0]
            array = [
                ["-R", "change files and directories recursively" ], 
                ["-f", "suppress most error messages" ]
            ]
            completion2(array, editing, sqort, dqort, last_sqort, last_dqort, true, 2)

            return 3
            
        elsif editing_position == 1
            if editing.index('+') == nil && editing.index('-') == nil && editing.index('=') == nil
                array = [
                    [editing + "a", "all"],
                    [editing + "g", "group"],
                    [editing + "o", "others"],
                    [editing + "u", "user"],
                    [editing + "+", "set flag"],
                    [editing + "-", "unset flag"],
                    [editing + "=", "?"]
                ]
                completion2(array, editing, sqort, dqort, last_sqort, last_dqort, false, 10)
    
                return 3
    
            else
                array = [
                    [editing + "l", "mandatory locking"],
                    [editing + "r", "read"],
                    [editing + "s", "set uid/gid"],
                    [editing + "t", "sticky"],
                    [editing + "w", "write"],
                    [editing + "x", "execute"]
                ]
    
                completion2(array, editing, sqort, dqort, last_sqort, last_dqort, false, 10)
            
                return 3
            end
        end

    ### tar ############################################################
    elsif cmd == "tar"
    
        if editing_position == 1
            array = [
                [editing + "A", "append to an archive"],
                [editing + "c", "create a new archive"],
                [editing + "f", "specify archive file or device"],
                [editing + "t", "list archive contents"],
                [editing + "u", "update archive"],
                [editing + "v", "verbose output"],
                [editing + "x", "extract files from an archive"],
                [editing + "z", "compress the resulting archive with gzip"],
                [editing + "j", "compress the resulting archive with bzip2"]
            ]
            completion2(array, editing, sqort, dqort, last_sqort, last_dqort, false, 10)

            return 3

        end

    ### chown ############################################################
    elsif cmd == "chown"
    
        if editing.size>=1 && editing[0] == "-"[0]
            array = [
                ["-R", "change files and directories recursively" ], 
                ["-f", "don't report errors" ],
                ["-h", "operate on symlinks them self"]
            ]
            completion2(array, editing, sqort, dqort, last_sqort, last_dqort, true, 2)

            return 3
            
        elsif editing_position == 1
           completion(user_names, editing, sqort, dqort, last_sqort, last_dqort, true)

            return 3

        end

    ### configure ############################################################
    elsif cmd == "./configure"
        if editing.index("=")
            if editing_dir == ""
                completion_mask(editing_dir, editing_file[editing_file.index("=")+1..editing_file.size], editing[editing.index("=")+1..editing.size], sqort, dqort, last_sqort, last_dqort, true, '.+')
            else
                completion_mask(editing_dir[editing_dir.index("=")+1..editing_dir.size], editing_file, editing[editing.index("=")+1..editing.size], sqort, dqort, last_sqort, last_dqort, true, '.+')
            end

            return 3
        elsif editing.index("--") == 0
            array = []

            if File.executable?("configure")
                `./configure --help`.each do |line|
                    line.scan(/(--[A-Za-z0-9\-]+)/) do |ar|
                        array.push("#{ar}")
                    end
                end
            end

            array.uniq!
            array.sort!

            completion(array, editing, sqort, dqort, last_sqort, last_dqort, false)

            return 3
            
        end
        
    ### make ############################################################
    elsif cmd == "make"
        if editing_before == "-C" || editing_before == "-I"
            completion_mask(editing_dir, editing_file, editing, sqort, dqort, last_sqort, last_dqort, true, '.+/')
            return 3

        elsif editing_before == "-j" || editing_before == "-l"
            return 2
            
        elsif editing_before == "-f" || editing_before == "-o" || editing_before == "-W"
                
            return 0
            
        elsif editing.index("=")
            if editing_dir == ""
                completion_mask(editing_dir, editing_file[editing_file.index("=")+1..editing_file.size], editing[editing.index("=")+1..editing.size], sqort, dqort, last_sqort, last_dqort, true, '.+')
            else
                completion_mask(editing_dir[editing_dir.index("=")+1..editing_dir.size], editing_file, editing[editing.index("=")+1..editing.size], sqort, dqort, last_sqort, last_dqort, true, '.+')
            end

            return 3
        else
            fname = ""
            
            i = 0
            while i < earray.size
                if earray[i] == "-f" && i+1 < earray.size
                    fname = earray[i + 1]
                    break
                end
                    
                i = i + 1
            end

            if fname == ""
                if File.exist?("GNUmakefile")
                    fname = "GNUmakefile"
                elsif File.exist?("makefile")
                    fname = "makefile"
                elsif File.exist?("Makefile")
                    fname = "Makefile"
                end
            end

            if fname != ""
                begin
                    command = []
                    File.new(fname).each{ |line|
                        tmp = line.split(":")

                        if tmp.size == 2 && tmp[0].index("$") == nil && tmp[0].index("\t") == nil
                            command.push(tmp[0])
                        end
                    }

                    if command.size > 0
                        completion(command, editing, sqort, dqort, last_sqort, last_dqort, true)
                    end
                rescue SystemCallError
                end
            end
                
            return 3
        end

    ### ssh-keygen ############################################################
    elsif cmd == "ssh-keygen"
        if editing.size>=1 && editing[0] == "-"[0]
            array = [
                ["-B", "show the bubblebabble digest of key"],
                ["-C", "provide new comment"],
                ["-D", "download key stored in smartcard reader"],
                ["-N", "provide new passphrase"],
                ["-P", "provide old passphrase"],
                ["-U", "upload key to smartcard reader"],
                ["-b", "specify number of bits in key"],
                ["-c", "change comment in private and public key files"],
                ["-e", "export key to SECSH file format"],
                ["-f", "key file"],
                ["-i", "import key to OpenSSH format"],
                ["-l", "show fingerprint of key file"],
                ["-p", "change passphrase of private key file"],
                ["-q", "silence ssh-keygen"],
                ["-t", "specify the type of the key to create"],
                ["-y", "get public key from private key"]
            ]

            completion2(array, editing, sqort, dqort, last_sqort, last_dqort, true, 3)

            return 3

        elsif editing_before == "-t"
            array = [ "dsa", "rsa", "rsa1" ]
            completion(array, editing, sqort, dqort, last_sqort, last_dqort, true)
            return 3
        end

    ### portupgrade ##########################################################
    elsif cmd == "portupgrade"
        if editing.size>=1 && editing[0] == "-"[0]
            array = [
                ["-A", "run a command after each installation"],
                ["-B", "run a command before each build"],
                ["-C", "clean after each install(default)"],
                ["-D", "distclean before each fetch or build"],
                ["-F", "fetch only"],
                ["-L", "output build/install log to files"],
                ["-M", "specify make(1) before-arguments"],
                ["-N", "install a new one when no installed package is found"],
                ["-O", "omit sanity check"],
                ["-P", "use package (specified twice, use packages only)"],
                ["-R", "do upward recursively"],
                ["-S", "specify alternative command to sudo(8)"],
                ["-W", "do not clean after each install"],
                ["-a", "all packages"],
                ["-b", "keep backup packages of the old versions"],
                ["-c", "clean before each build (default)"],
                ["-f", "force upgrade even if it is to be a downgrade or just a reinstall"],
                ["-i", "be interactive"],
                ["-k", "force upgrade even if some of the requistite ports have failed"],
                ["-l", "output result to a file"],
                ["-m", "specify make(1) after-arguments"],
                ["-n", "do not execute any installation or upgrade"],
                ["-o", "specify the following package's origin"],
                ["-p", "make package"],
                ["-q", "do not read pkgtools.conf"],
                ["-r", "do recursively"],
                ["-s", "run commands under sudo(8) where needed"],
                ["-u", "do not preserve old shared libraries"],
                ["-v", "be verbose"],
                ["-w", "do not clean before each build"],
                ["-x", "exclude packages"]
            ]

            completion2(array, editing, sqort, dqort, last_sqort, last_dqort, true, 3)

            return 3

        else
            output = `pkg_info | awk '{ print $1; }'`

            if output != ""
                array = output.split

                array.sort!

                completion(array, editing, sqort, dqort, last_sqort, last_dqort, true)

                return 3
            end
        end

    ### pkg_add ############################################################
    elsif cmd == "pkg_add"
        if editing.size>=1 && editing[0] == "-"[0]
            array = [
                ["-I", "don't execute installation scripts"],
                ["-M", "run in master mode"],
                ["-R", "don't record"],
                ["-S", "run in slave mode"],
                ["-f", "force installation"],

                ["-n", "don't really install packages"],
                ["-p", "specify prefix"],
                ["-r", "fetch from remote site"],
                ["-t", "specify mktemp template"],
                ["-v", "be verbose"]
            ]

            completion2(array, editing, sqort, dqort, last_sqort, last_dqort, true, 3)

            return 3
        end

    ### pkg_delete ############################################################
    elsif cmd == "pkg_delete"
        if editing.size>=1 && editing[0] == "-"[0]
            array = [
                ["-D", "don't execute deinstallation scripts"],
                ["-G", "do not expand glob patterns"],
                ["-a", "delete all installed packages"],
                ["-d", "remove empty directories"],
                ["-f", "force deinstallation"],
                ["-i", "be interactive"],
                ["-n", "don't really deinstall packages"],
                ["-p", "specify prefix"],
                ["-r", "delete recursively"],
                ["-v", "be verbose"],
                ["-x", "use regular expression"]
            ]

            completion2(array, editing, sqort, dqort, last_sqort, last_dqort, true, 3)

            return 3

        elsif editing_before == "-p"
            array = [ "installed", "ports-supfile" ]
            completion(array, editing, sqort, dqort, last_sqort, last_dqort, true)
            return 3


        else
            output = `pkg_info | awk '{ print $1; }'`

            if output != ""
                array = output.split

                array.sort!

                completion(array, editing, sqort, dqort, last_sqort, last_dqort, true)

                return 3
            end
        end

    ### pkg_info ############################################################
    elsif cmd == "pkg_info"
        if editing.size>=1 && editing[0] == "-"[0]
            array = [
                ["-D", "show install-message files"],
                ["-G", "do not expand glob patterns"],
                ["-I", "show index lines"],
                ["-L", "show full pathnames of files"],
                ["-R", "show list list of installed requiring packages"],
                ["-W", "show which package the file belongs to"],
                ["-a", "show all installed packages"],
                ["-c", "show comment fields"],
                ["-d", "show long descriptions"],
                ["-e", "test if package is installed"],
                ["-f", "show packing list instructions"],
                ["-g", "show files that's modified"],
                ["-i", "show install scripts"],
                ["-k", "show deinstall scripts"],
                ["-l", "specify prefix string"],
                ["-m", "show mtree files"],
                ["-o", "show origin"],
                ["-p", "show installation prefixes"],
                ["-q", "be quiet"],
                ["-r", "show requirements scripts"],
                ["-s", "show total size occupied by each package"],
                ["-t", "specify mktemp template"],
                ["-v", "be verbose"],
                ["-x", "use regular expression"],
            ]

            completion2(array, editing, sqort, dqort, last_sqort, last_dqort, true, 3)
            array.sort!

            return 3

        elsif editing_before == "-W" || editing_before == "-t"
            array = [ "installed", "ports-supfile" ]
            completion(array, editing, sqort, dqort, last_sqort, last_dqort, true)
            return 3

        else
            output = `pkg_info | awk '{ print $1; }'`

            if output != ""
                array = output.split

                array.sort!

                completion(array, editing, sqort, dqort, last_sqort, last_dqort, true)

                return 3
            end
        end

    ### ssh ############################################################
    elsif cmd == "ssh" then
        earray.each { |str|
            if str == "-l" || str == "-b" || str == "-D" || str == "-e" || str == "-L" || str == "-m" || str == "-p" || str == "-R" || str == "-c" || str == "-o" || str == "-F" || str == "-i"
                editing_position = editing_position -1
            end
        }
    
        if editing.size>=1 && editing[0] == "-"[0]
            array = [
                ["-1", "forces ssh to try protocol version 1 only"],
                ["-2", "forces ssh to try protocol version 2 only"],
                ["-4", "forces ssh to use IPv4 addresses only"],
                ["-6", "forces ssh to use IPv6 addresses only"],
                ["-A", "enables forwarding of the authentication agent connection"],
                ["-C", "compress data"],
                ["-D", "specify a dynamic port forwarding"],
                ["-F", "specify alternate config file"],
                ["-I", "specify smartcard device"],
                ["-L", "specify local port forwarding"],
                ["-N", "do not execute a remote command. (protocol version 2 only)"],
                ["-P", "use non privileged port"],
                ["-R", "specify remote port forwarding"],
                ["-T", "disable pseudo-tty allocation (protocol version 2 only)"],
                ["-V", "show version number"],
                ["-X", "enable X11 forwarding"],
                ["-a", "disable forwarding of authentication agent connection"],
                ["-b", "specify interface to transmit on"],
                ["-c", "select encryption cipher"],
                ["-e", "set escape character"],
                ["-f", "go to background"],
                ["-g", "allow remote hosts to connect to local forwarded ports"],
                ["-i", "select identity file"],
                ["-k", "disable forwarding of kerberos tickets"],
                ["-l", "specify login name"],
                ["-m", "specify mac algorithms"],
                ["-n", "redirect stdin from /dev/null"],
                ["-o", "specify extra options"],
                ["-p", "specify port on remote host"],
                ["-q", "quiet operation"],
                ["-s", "invoke subsystem"],
                ["-t", "force pseudo-tty allocation"],
                ["-v", "verbose mode"],
                ["-x", "disable X11 forwarding"]
            ]
            completion2(array, editing, sqort, dqort, last_sqort, last_dqort, true, 3)

            return 3

        elsif editing_before == "-l"
            array = user_names
            completion(array, editing, sqort, dqort, last_sqort, last_dqort, true)
            
            return 3

        elsif editing_before == "-b" || editing_before == "-D" || editing_before == "-e" || editing_before == "-L" || editing_before == "-m" || editing_before == "-p" || editing_before == "-R" 
            return 2

        elsif editing_before == "-c"
            array = ["3des", "arcfour", "blowfish", "des", "idea", "none", "tss"]
            completion(array, editing, sqort, dqort, last_sqort, last_dqort, true)
            
            return 3

        elsif editing_before == "-o"
            if editing.index('=') == nil
                array = ["AFSTokenPassing=", "KerberosAuthentication=",
                         "AddressFamily=", "KerberosTgtPassing=",
                         "BatchMode=", "LocalForward=",
                         "BindAddress=", "LogLevel=",
                         "ChallengeResponseAuthentication=", "MACs=",
                         "CheckHostIP=", "NoHostAuthenticationForLocalhost=",
                         "Cipher=",  "NumberOfPasswordPrompts=",
                         "Ciphers=", "PasswordAuthentication=",
                         "ClearAllForwardings=", "Port=",
                         "Compression=",     "PreferredAuthentications=",
                         "CompressionLevel=",  "Protocol=",
                         "ConnectTimeout=",    "ProtocolKeepAlives=",
                         "ConnectionAttempts=", "ProxyCommand=",
                         "DynamicForward=",    "PubkeyAuthentication=",
                         "EnableSSHKeysign=",  "RSAAuthentication=",
                         "EscapeChar=",        "RemoteForward=",
                         "FallBackToRsh=",     "RhostsAuthentication=",
                         "ForwardAgent=",      "RhostsRSAAuthentication=",
                         "ForwardX11=",        "ServerAliveCountMax=",
                         "ForwardX11Trusted=", "ServerAliveInterval=",
                         "GSSAPIAuthentication=", "SetupTimeOut=",
                         "GSSAPIDelegateCredentials=", "SmartcardDevice=",
                         "GatewayPorts=",     "StrictHostKeyChecking=",
                         "GlobalKnownHostsFile=",  "TCPKeepAlive=",
                         "HostKeyAlgorithms=",        "UsePrivilegedPort=",
                         "HostKeyAlias=",             "UseRsh=",
                         "HostName=",                   "User=",
                         "HostbasedAuthentication=",  "UserKnownHostsFile=",
                         "IdentitiesOnly=",            "VerifyHostKeyDNS=",
                         "IdentityFile=",            "XAuthLocation=",
                         "KeepAlive="]

                completion(array, editing, sqort, dqort, last_sqort, last_dqort, false);

                return 3
            else
                array = ["no", "yes"]

                completion(array, editing[editing.index("=")+1..editing.size], sqort, dqort, last_sqort, last_dqort, true);

                return 3
            end
            
        elsif editing_before == "-F" || editing_before == "-i"
            return 0
        
        elsif editing_position == 1
            exist_l = false
            earray.each{|str|
                if str.index("-l") == 0
                    exist_l = true
                end
            }
            
            if exist_l 
                completion(host_names, editing, sqort, dqort, last_sqort, last_dqort, true)
                return 3
            else 
                if editing.index('@') == nil
                    array = []
                    user_names.each {|name|
                        array.push(name + "@")
                    }
                    completion(array, editing, sqort, dqort, last_sqort, last_dqort, false)

                    return 3
                else
                    user = editing[0..editing.index('@')]
                    array = []
                    host_names.each {|name|
                        array.push(user + name)
                    }
                    completion(array, editing, sqort, dqort, last_sqort, last_dqort, true)
    
                    return 3
                end
            end
        elsif editing_position == 2
            return 1
        end
    end

    return 0
end
