Linux CLI 50 🐧 groff command
groff > file
Hello Linux
# Ctrl + D to quit
groff -Thtml
groff -Thtml > index.html
groff is the GNU implementation of the classic Unix troff typesetting system. It takes plain text with embedded formatting macros and produces typeset output — plain text, PostScript, PDF, HTML, or UTF-8. Its most important modern job is rendering man pages, but it can also produce nicely formatted documents.
Key point: groff is a formatter, not a word processor. You write plain text interspersed with requests (lines starting with a dot, like .sp or .ce) and macros (higher-level commands from a macro package like man or ms). groff then renders that into the output format of your choice.
a – groff command introduction
groff is used to create simple text documents and troff (TeX-like) formats. It uses macros similar to those used by Unix typesetters. It is mainly used to create man pages — the built-in documentation you see with man ls, man grep, etc.
Syntax:
groff [options] [file...]
Common options:
| Option | Purpose |
|---|---|
-T dev | Direct output to device dev |
-i | Read stdin after all named input files |
-m dir | Search dir for macro files |
-n num | Start numbering at page num |
-t | Process with tbl (tables) |
-p | Process with pic (diagrams) |
-e | Process with eqn (equations) |
-s | Process with soelim (include files) |
Available output devices:
| Device | Output |
|---|---|
ps | PostScript |
pdf | |
ascii | Plain ASCII text |
utf8 | UTF-8 encoded text |
html | HTML |
dvi | DVI (via TeX) |
lj4 | HP LaserJet 4 |
latin1 | ISO Latin-1 |
Basic usage — writing directly to a file:
$ groff > file
Hello Linux
# Ctrl + D to quit
$ cat file
Hello Linux
When you run groff with no input files, it reads from stdin until you press Ctrl+D. The output goes to stdout, which you redirect to a file.
More examples:
# Send output to HTML
$ groff -Thtml
# Format a file to HTML and save it
$ groff -Thtml > index.html
# Convert a man page to HTML
$ man -P cat cat | groff -Thtml > cat.html
# Format a file to PDF
$ groff -Tpdf document.ms > output.pdf
# Format a file to plain text
$ groff -Tascii document.ms
# Format with UTF-8 output
$ groff -Tutf8 document.ms
# Process tables too
$ groff -t -Tpdf report.ms > report.pdf
# Start page numbering at 5
$ groff -n 5 document.ms
# Read stdin after files
$ groff -i document.ms
# Use a custom macro directory
$ groff -m /usr/share/groff/site-tmac document.ms
Note: By itself,
groffdoes very little — it just renders text. The real power comes from macro packages likeman,ms,me, andmm, which provide higher-level commands (headings, paragraphs, lists, fonts). When you use-man, you get the macros used in manual pages. When you use-ms, you get a package designed for technical documents.
Common macro packages:
| Package | Flag | Purpose |
|---|---|---|
man | -man | Manual pages |
mdoc | -mdoc | BSD-style manual pages |
ms | -ms | Manuscripts, technical papers |
me | -me | General documents |
mm | -mm | Memos, letters, reports |
# Render a man page
$ groff -man -Tascii mytool.1
# Render a document with the ms macros
$ groff -ms -Tpdf paper.ms > paper.pdf
# Render with the mm macros
$ groff -mm -Tps letter.mm > letter.ps
b – some groff embedded commands
groff input contains requests — lines that start with a dot and a two-letter command. These control spacing, alignment, indentation, and more. Here are the most common ones.
Spacing:
| Request | Effect |
|---|---|
.sp | Space down one line |
.sp 5 | Space down 5 lines |
.sp 2.5c | Space 2.5 centimeters |
.br | Line break |
.bp | Page break |
Centering and alignment:
| Request | Effect |
|---|---|
.ce 100 | Center the next 100 lines |
.ce 0 | Stop centering |
.ad l | Adjust lines left |
.ad r | Adjust lines right |
.ad c | Adjust lines center |
.ad b | Adjust lines both margins |
.na | No adjustment |
Indentation:
| Request | Effect |
|---|---|
.in | Indent one level |
.in 4 | Indent 4 lines |
.ti | Temporary indent (next line only) |
.po 10 | Page offset — 10 characters |
Font and size:
| Request | Effect |
|---|---|
.ps 20 | Font size 20 |
.ss 12 | Space-character size |
.ft B | Switch to bold font |
.ft I | Switch to italic font |
.ft R | Return to roman font |
Example — a simple formatted document:
$ cat > hello.tr << 'EOF'
.ce 1
Hello, Linux!
.sp 2
This is a simple groff document.
.sp
It has several lines of text,
with some spacing in between.
.in 4
This line is indented.
.in 0
Back to normal.
.ce 0
.sp 2
The end.
EOF
$ groff -Tascii hello.tr
Hello, Linux!
This is a simple groff document.
It has several lines of text,
with some spacing in between.
This line is indented.
Back to normal.
The end.
More details: The full troff request reference is at https://www.troff.org/54.pdf.
c – groff examples
Here are the practical examples you’ll use most often.
1. Format text as HTML interactively:
$ groff -Thtml
Hello, Linux!
This is formatted by groff.
^D
<!-- Creator: groff version 1.22.4 -->
<!-- CreationDate: ... -->
<!-- ... -->
<p>Hello, Linux!
This is formatted by groff.</p>
2. Save formatted HTML to a file:
$ groff -Thtml > index.html
Hello, Linux!
^D
$ ls -l index.html
-rw-r--r-- 1 kronos kronos 1234 Jan 15 10:00 index.html
3. Create a source file and render it:
$ echo "hello, Linux!" > hello.tr
$ cat hello.tr
hello, Linux!
$ groff hello.tr
hello, Linux!
4. Create a PDF from a groff source:
$ groff -Tpdf hello.tr > output.pdf
$ file output.pdf
output.pdf: PDF document, version 1.4
5. Convert a man page to HTML:
$ man -P cat cat | groff -Thtml > cat.html
$ ls -l cat.html
-rw-r--r-- 1 kronos kronos 45678 Jan 15 10:00 cat.html
The man -P cat part tells man to use cat as the pager — so it just dumps the raw roff source to stdout instead of displaying it. That source is then fed to groff -Thtml.
More examples:
# Write a formatted document with macros
$ cat > report.ms << 'EOF'
.TL
My Report
.AU
Kronos
.AB
This is the abstract.
.AE
.NH
Introduction
.PP
This is the first paragraph.
.NH
Methods
.PP
This is the second paragraph.
EOF
$ groff -ms -Tpdf report.ms > report.pdf
# Format a man page to plain text
$ man -P cat ls | groff -man -Tascii | head -20
# Convert a man page to PDF
$ man -P cat ls | groff -man -Tpdf > ls.pdf
# Convert a man page to UTF-8 text
$ man -P cat ls | groff -man -Tutf8
# Strip formatting entirely
$ man -P cat ls | groff -man -Tascii | col -bx
# Interactive session to HTML
$ groff -Thtml > page.html
.ce 1
Welcome
.sp 2
This is a groff-generated page.
^D
Comparing output formats:
# ASCII
$ groff -Tascii hello.tr
hello, Linux!
# UTF-8
$ groff -Tutf8 hello.tr
hello, Linux!
# HTML
$ groff -Thtml hello.tr
<!-- Creator: groff version 1.22.4 -->
<p>hello, Linux!</p>
# PDF (binary)
$ groff -Tpdf hello.tr > hello.pdf
$ file hello.pdf
hello.pdf: PDF document, version 1.4
A full example — a simple man page:
$ cat > mytool.1 << 'EOF'
.TH MYTOOL 1 "January 2024" "mytool 1.0" "User Commands"
.SH NAME
mytool \- a simple example
.SH SYNOPSIS
.B mytool
[\fIOPTION\fR]... [\fIFILE\fR]...
.SH DESCRIPTION
.B mytool
does something useful.
.SH OPTIONS
.TP
.B \-h
Show help.
.TP
.B \-v
Show version.
.SH AUTHOR
Written by Kronos.
EOF
# Render it like man would
$ groff -man -Tascii mytool.1
# Convert to HTML
$ groff -man -Thtml mytool.1 > mytool.html
# Convert to PDF
$ groff -man -Tpdf mytool.1 > mytool.pdf
# Install it
$ sudo cp mytool.1 /usr/share/man/man1/
$ man mytool
Complete Example Session
# ============================================
# PART 1: BASIC GROFF — WRITE TO A FILE
# ============================================
$ groff > file
Hello Linux
# Ctrl + D to quit
$ cat file
Hello Linux
# ============================================
# PART 2: FORMAT AS HTML
# ============================================
$ groff -Thtml
Hello, Linux!
^D
<!-- Creator: groff version 1.22.4 -->
<!-- CreationDate: Mon Jan 15 10:00:00 2024 -->
<p>Hello, Linux!</p>
# ============================================
# PART 3: SAVE HTML TO FILE
# ============================================
$ groff -Thtml > index.html
Hello, Linux!
^D
$ ls -l index.html
-rw-r--r-- 1 kronos kronos 1234 Jan 15 10:00 index.html
$ head index.html
<!-- Creator: groff version 1.22.4 -->
<p>Hello, Linux!</p>
# ============================================
# PART 4: SIMPLE SOURCE FILE
# ============================================
$ echo "hello, Linux!" > hello.tr
$ groff hello.tr
hello, Linux!
# ============================================
# PART 5: CREATE A PDF
# ============================================
$ groff -Tpdf hello.tr > output.pdf
$ file output.pdf
output.pdf: PDF document, version 1.4
# ============================================
# PART 6: MAN PAGE TO HTML
# ============================================
$ man -P cat cat | groff -Thtml > cat.html
$ ls -lh cat.html
-rw-r--r-- 1 kronos kronos 45K Jan 15 10:00 cat.html
# ============================================
# PART 7: FORMATTED DOCUMENT WITH MACROS
# ============================================
$ cat > report.ms << 'EOF'
.TL
My Report
.AU
Kronos
.NH
Introduction
.PP
This is the first paragraph of the report.
.NH
Conclusion
.PP
This is the conclusion.
EOF
$ groff -ms -Tascii report.ms
My Report
Kronos
1. Introduction
This is the first paragraph of the report.
2. Conclusion
This is the conclusion.
# ============================================
# PART 8: EMBEDDED REQUESTS
# ============================================
$ cat > hello.tr << 'EOF'
.ce 1
Hello, Linux!
.sp 2
This is a simple groff document.
.sp
It has several lines of text.
.in 4
This line is indented.
.in 0
Back to normal.
.ce 0
.sp 2
The end.
EOF
$ groff -Tascii hello.tr
Hello, Linux!
This is a simple groff document.
It has several lines of text.
This line is indented.
Back to normal.
The end.
# ============================================
# PART 9: MAN PAGE TO PDF
# ============================================
$ man -P cat ls | groff -man -Tpdf > ls.pdf
$ file ls.pdf
ls.pdf: PDF document, version 1.4
# ============================================
# PART 10: MAN PAGE TO UTF-8
# ============================================
$ man -P cat ls | groff -man -Tutf8 | head -20
LS(1) User Commands LS(1)
NAME
ls - list directory contents
SYNOPSIS
ls [OPTION]... [FILE]...
DESCRIPTION
List information about the FILEs (the current directory by
default).
...
Quick Reference
groff — Options
| Option | Purpose |
|---|---|
-T dev | Output device (ascii, utf8, html, pdf, ps) |
-i | Read stdin after files |
-m dir | Macro directory |
-n num | First page number |
-t | Process with tbl |
-p | Process with pic |
-e | Process with eqn |
-s | Process with soelim |
groff — Output Devices
| Device | Output |
|---|---|
ascii | Plain ASCII |
utf8 | UTF-8 text |
html | HTML |
pdf | |
ps | PostScript |
dvi | DVI |
lj4 | HP LaserJet 4 |
latin1 | ISO Latin-1 |
groff — Macro Packages
| Flag | Package | Purpose |
|---|---|---|
-man | man | Manual pages |
-mdoc | mdoc | BSD man pages |
-ms | ms | Manuscripts |
-me | me | General documents |
-mm | mm | Memos, letters |
groff — Common Requests
| Request | Effect |
|---|---|
.sp N | Space N lines |
.br | Line break |
.bp | Page break |
.ce N | Center N lines |
.ce 0 | Stop centering |
.in N | Indent N |
.ti | Temporary indent |
.po N | Page offset |
.ps N | Font size |
.ss N | Space-character size |
.ad l|r|c|b | Adjust lines |
.na | No adjustment |
.ft B | Bold font |
.ft I | Italic font |
.ft R | Roman font |
man page Macros
| Macro | Purpose |
|---|---|
.TH | Title header |
.SH | Section header |
.SS | Subsection |
.PP | Paragraph |
.TP | Tagged paragraph |
.B | Bold |
.I | Italic |
.BR | Bold-roman alternating |
.IR | Italic-roman alternating |
groff vs Other Tools
| Tool | Purpose |
|---|---|
groff | Troff typesetting |
TeX/LaTeX | High-quality typesetting |
pandoc | Document conversion |
man | View man pages |
mandoc | Man page compiler |
Best Practices
✅ Do This:
# Use -man for man pages
groff -man -Tascii mytool.1 # ✅
# Use -Tpdf for PDF output
groff -Tpdf -ms doc.ms > doc.pdf # ✅
# Use -Thtml for HTML
groff -Thtml -man mytool.1 > mytool.html # ✅
# Use macro packages for structured documents
groff -ms -Tpdf report.ms > report.pdf # ✅
# Preview in ASCII first
groff -Tascii doc.ms # ✅
# Use .ce 0 to stop centering
.ce 0 # ✅
# Pipe man source through groff for conversion
man -P cat ls | groff -man -Thtml > ls.html # ✅
❌ Don’t Do This:
# Don't forget the macro package
groff -Tpdf doc.ms # ❌ no macros — plain text
# Don't mix -T devices
groff -Tpdf -Thtml doc.ms # ❌ only last wins
# Don't use groff for simple text output
groff -Tascii file.txt # ⚠️ just cat it
# Don't forget .ce 0 after centering
.ce 100 # ❌ centers forever
# Don't assume all devices are installed
groff -Tpdf doc.ms # ❌ may need ghostscript
# Don't use groff for modern documentation
# Consider Markdown + pandoc instead # ✅
Common Pitfalls
| Pitfall | Problem | Solution |
|---|---|---|
| No output device | Confusing error | Use -T |
| No macro package | Plain text only | Add -man or -ms |
| Missing requests | Layout broken | Check dot-prefix |
| PDF needs Ghostscript | Error | Install ghostscript |
| HTML missing CSS | Ugly output | Post-process |
.ce never stopped | Centered forever | Add .ce 0 |
| Requests must start at col 1 | Not processed | No leading spaces |
| Trailing spaces | Unexpected output | Clean input |
Real-World Examples
1. Write Text and Save as Plain File
$ groff > note.txt
Hello, this is a note.
^D
$ cat note.txt
Hello, this is a note.
2. Format as HTML
$ groff -Thtml > page.html
Hello, Linux!
^D
3. Save HTML to a File
$ groff -Thtml > index.html
Hello, Linux!
^D
$ ls -l index.html
-rw-r--r-- 1 kronos kronos 1234 Jan 15 10:00 index.html
4. Create a Simple Source File
$ echo "hello, Linux!" > hello.tr
$ groff hello.tr
hello, Linux!
5. Create a PDF
$ groff -Tpdf hello.tr > output.pdf
$ file output.pdf
output.pdf: PDF document, version 1.4
6. Man Page to HTML
$ man -P cat cat | groff -Thtml > cat.html
$ ls -lh cat.html
-rw-r--r-- 1 kronos kronos 45K Jan 15 10:00 cat.html
7. Man Page to PDF
$ man -P cat ls | groff -man -Tpdf > ls.pdf
$ ls -lh ls.pdf
-rw-r--r-- 1 kronos kronos 78K Jan 15 10:00 ls.pdf
8. Formatted Document with ms Macros
$ cat > report.ms << 'EOF'
.TL
My Report
.AU
Kronos
.NH
Introduction
.PP
This is the first paragraph.
.NH
Conclusion
.PP
This is the conclusion.
EOF
$ groff -ms -Tpdf report.ms > report.pdf
9. Centered Title
$ cat > title.tr << 'EOF'
.ce 1
My Document
.sp 2
.ce 0
This is the body of the document.
EOF
$ groff -Tascii title.tr
My Document
This is the body of the document.
10. Indented Paragraphs
$ cat > indent.tr << 'EOF'
Normal line.
.in 4
Indented line.
.in 8
More indented line.
.in 0
Back to normal.
EOF
$ groff -Tascii indent.tr
Normal line.
Indented line.
More indented line.
Back to normal.
11. Write a Complete Man Page
$ cat > mytool.1 << 'EOF'
.TH MYTOOL 1 "January 2024" "mytool 1.0" "User Commands"
.SH NAME
mytool \- a simple example tool
.SH SYNOPSIS
.B mytool
[\fIOPTION\fR]... [\fIFILE\fR]...
.SH DESCRIPTION
.B mytool
does something useful with the given files.
.SH OPTIONS
.TP
.B \-h
Show help and exit.
.TP
.B \-v
Show version and exit.
.SH AUTHOR
Written by Kronos.
EOF
$ groff -man -Tascii mytool.1
12. Convert All Man Pages to HTML
$ mkdir -p html-man
$ for m in $(man -k . | awk '{print $1}' | sort -u | head -20); do
man -P cat "$m" 2>/dev/null | groff -man -Thtml > "html-man/$m.html"
done
$ ls html-man/
13. Strip Formatting from a Man Page
$ man -P cat ls | groff -man -Tascii | col -bx
14. Process Tables with tbl
$ cat > table.ms << 'EOF'
.TS
allbox;
c c c
l l l.
Name Dept Score
Alice Eng 95
Bob Math 87
.TE
EOF
$ groff -t -ms -Tascii table.ms
15. Use a Different Macro Package
# Manuscript macros
$ groff -ms -Tpdf paper.ms > paper.pdf
# Memo macros
$ groff -mm -Tps letter.mm > letter.ps
# General document macros
$ groff -me -Tascii doc.me
16. Pipe a Man Page Through a Pager
$ man -P cat ls | groff -man -Tutf8 | less
17. Generate a PDF Report
$ cat > report.ms << 'EOF'
.TL
Monthly Report
.AU
Kronos
.AB
Summary of January activity.
.AE
.NH
Highlights
.PP
We accomplished several key goals.
.NH
Next Steps
.PP
Continue working on the roadmap.
EOF
$ groff -ms -Tpdf report.ms > report.pdf
$ xdg-open report.pdf
18. Preview Before Converting
# Always preview in ASCII first
$ groff -Tascii document.ms
# Then convert to your target format
$ groff -Tpdf document.ms > document.pdf
Visual: How groff Works
┌──────────────────────────────────────────────┐
│ groff pipeline │
│ │
│ Source (.ms, .man, .tr) │
│ ┌────────────────────────────────────────┐ │
│ │ .TL │ │
│ │ My Report │ │
│ │ .AU │ │
│ │ Kronos │ │
│ │ .PP │ │
│ │ Body text here. │ │
│ └────────────────────────────────────────┘ │
│ │
│ │ │
│ ▼ │
│ │
│ groff -ms -Tpdf │
│ (reads macros, applies formatting) │
│ │
│ │ │
│ ▼ │
│ │
│ Output (PDF, HTML, ASCII, ...) │
│ ┌────────────────────────────────────────┐ │
│ │ ┌──────────────────┐ │ │
│ │ │ My Report │ │ │
│ │ │ │ │ │
│ │ │ Kronos │ │ │
│ │ │ │ │ │
│ │ │ Body text here.│ │ │
│ │ └──────────────────┘ │ │
│ └────────────────────────────────────────┘ │
│ │
└──────────────────────────────────────────────┘
Summary
| Command | Purpose | Example |
|---|---|---|
groff > file | Write to file | groff > out.txt |
groff -Tascii | Plain text output | groff -Tascii doc.ms |
groff -Tutf8 | UTF-8 output | groff -Tutf8 doc.ms |
groff -Thtml | HTML output | groff -Thtml doc.ms |
groff -Tpdf | PDF output | groff -Tpdf doc.ms > doc.pdf |
groff -Tps | PostScript | groff -Tps doc.ms > doc.ps |
groff -man | Man page macros | groff -man -Tascii mytool.1 |
groff -ms | Manuscript macros | groff -ms -Tpdf report.ms |
groff -mm | Memo macros | groff -mm -Tps letter.mm |
groff -t | Process tables | groff -t -ms -Tpdf report.ms |
groff -n N | Start page at N | groff -n 5 doc.ms |
.sp N | Space N lines | .sp 2 |
.ce N | Center N lines | .ce 1 |
.in N | Indent N | .in 4 |
.ps N | Font size | .ps 12 |
.bp | Page break | .bp |
.br | Line break | .br |
Key takeaways:
groffis the GNU troff typesetting system — a formatter, not a word processor- It’s mainly used for man pages, but can produce PDF, HTML, PS, and plain text
- Use
-T devto choose the output device (ascii,utf8,html,pdf,ps) - Use macro packages like
-man(man pages) and-ms(manuscripts) for structured documents - Requests start with a dot (
.sp,.ce,.in,.ps,.bp,.br) and control layout - Run
groffwith no file to read from stdin; Ctrl+D to finish - Convert a man page with
man -P cat NAME | groff -man -Thtml > NAME.html - Create a PDF with
groff -ms -Tpdf doc.ms > doc.pdf - Preview in ASCII first (
-Tascii) before converting to PDF or HTML - You can also just use
manto view pages —groffis for generating or converting them
Remember: groff is powerful but quirky. Its syntax is terse and its history is long. For modern documentation, Markdown + pandoc is usually a better choice. But for man pages and for converting existing troff sources, groff is the right tool. Learn -man and -ms, the basic requests (.sp, .ce, .in), and the man -P cat | groff idiom for converting man pages. It’s a niche skill, but one that still pays off when you need to produce properly typeset Unix documentation.
Stop using slow, ad-bloated tool sites! 🤮
🔎 Search “KandZ Tools” on Google to use many professional utilities for free.
KandZ.me is the ultimate minimalist hub for:
✅ Finance (Mortgage, Interest, Inflation)
✅ Tech (Base64, JSON, Dev Suite, IP)
✅ Health (BMI, BMR, TDEE)
✅ Productivity (Timer, Workspace, QR)
⚡️ Fast & Private
🔒 No data leaves your device
💎 100% Free
🔗 Use it now: https://tools.kandz.me
🔖 Bookmark it—you’ll need it later!