diff --git a/documentation/content/en/books/developers-handbook/l10n/_index.adoc b/documentation/content/en/books/developers-handbook/l10n/_index.adoc index 219ec5ea2b..19838d15b2 100644 --- a/documentation/content/en/books/developers-handbook/l10n/_index.adoc +++ b/documentation/content/en/books/developers-handbook/l10n/_index.adoc @@ -1,211 +1,211 @@ --- title: Chapter 4. Localization and Internationalization - L10N and I18N authors: prev: books/developers-handbook/secure next: books/developers-handbook/policies description: Localization and Internationalization - L10N and I18N in FreeBSD tags: ["L10N", "I18N", "Localization", "Internationalization", "FreeBSD"] --- [[l10n]] = Localization and Internationalization - L10N and I18N :doctype: book :toc: macro :toclevels: 1 :icons: font :sectnums: :sectnumlevels: 6 :source-highlighter: rouge :experimental: :skip-front-matter: :xrefstyle: basic :relfileprefix: ../ :outfilesuffix: :sectnumoffset: 4 include::shared/mirrors.adoc[] include::shared/authors.adoc[] include::shared/releases.adoc[] include::shared/en/mailing-lists.adoc[] include::shared/en/teams.adoc[] include::shared/en/urls.adoc[] toc::[] [[l10n-programming]] == Programming I18N Compliant Applications To make your application more useful for speakers of other languages, we hope that you will program I18N compliant. The GNU gcc compiler and GUI libraries like QT and GTK support I18N through special handling of strings. Making a program I18N compliant is very easy. It allows contributors to port your application to other languages quickly. Refer to the library specific I18N documentation for more details. In contrast with common perception, I18N compliant code is easy to write. Usually, it only involves wrapping your strings with library specific functions. In addition, please be sure to allow for wide or multibyte character support. === A Call to Unify the I18N Effort It has come to our attention that the individual I18N/L10N efforts for each country has been repeating each others' efforts. Many of us have been reinventing the wheel repeatedly and inefficiently. We hope that the various major groups in I18N could congregate into a group effort similar to the Core Team's responsibility. Currently, we hope that, when you write or port I18N programs, you would send it out to each country's related FreeBSD mailing list for testing. In the future, we hope to create applications that work in all the languages out-of-the-box without dirty hacks. The {freebsd-i18n} has been established. If you are an I18N/L10N developer, please send your comments, ideas, questions, and anything you deem related to it. === Perl and Python Perl and Python have I18N and wide character handling libraries. Please use them for I18N compliance. [[posix-nls]] == Localized Messages with POSIX.1 Native Language Support (NLS) Beyond the basic I18N functions, like supporting various input encodings or supporting national conventions, such as the different decimal separators, at a higher level of I18N, it is possible to localize the messages written to the output by the various programs. A common way of doing this is using the POSIX.1 NLS functions, which are provided as a part of the FreeBSD base system. [[nls-catalogs]] === Organizing Localized Messages into Catalog Files POSIX.1 NLS is based on catalog files, which contain the localized messages in the desired encoding. The messages are organized into sets and each message is identified by an integer number in the containing set. The catalog files are conventionally named after the locale they contain localized messages for, followed by the `.msg` extension. For instance, the Hungarian messages for ISO8859-2 encoding should be stored in a file called [.filename]#hu_HU.ISO8859-2#. These catalog files are common text files that contain the numbered messages. It is possible to write comments by starting the line with a `$` sign. Set boundaries are also separated by special comments, where the keyword `set` must directly follow the `$` sign. The `set` keyword is then followed by the set number. For example: [.programlisting] .... $set 1 .... The actual message entries start with the message number and followed by the localized message. The well-known modifiers from man:printf[3] are accepted: [.programlisting] .... 15 "File not found: %s\n" .... The language catalog files have to be compiled into a binary form before they can be opened from the program. This conversion is done with the man:gencat[1] utility. Its first argument is the filename of the compiled catalog and its further arguments are the input catalogs. The localized messages can also be organized into more catalog files and then all of them can be processed with man:gencat[1]. [[nls-using]] === Using the Catalog Files from the Source Code -Using the catalog files is simple. To use the related functions, [.filename]#nl_types.h# must be included. Before using a catalog, it has to be opened with man:catopen[3]. The function takes two arguments. The first parameter is the name of the installed and compiled catalog. Usually, the name of the program is used, such as grep. This name will be used when looking for the compiled catalog file. The man:catopen[3] call looks for this file in [.filename]#/usr/shared/nls/locale/catname# and in [.filename]#/usr/local/shared/nls/locale/catname#, where `locale` is the locale set and `catname` is the catalog name being discussed. The second parameter is a constant, which can have two values: +Using the catalog files is simple. To use the related functions, [.filename]#nl_types.h# must be included. Before using a catalog, it has to be opened with man:catopen[3]. The function takes two arguments. The first parameter is the name of the installed and compiled catalog. Usually, the name of the program is used, such as grep. This name will be used when looking for the compiled catalog file. The man:catopen[3] call looks for this file in [.filename]#/usr/share/nls/locale/catname# and in [.filename]#/usr/local/share/nls/locale/catname#, where `locale` is the locale set and `catname` is the catalog name being discussed. The second parameter is a constant, which can have two values: * `NL_CAT_LOCALE`, which means that the used catalog file will be based on `LC_MESSAGES`. * `0`, which means that `LANG` has to be used to open the proper catalog. The man:catopen[3] call returns a catalog identifier of type `nl_catd`. Please refer to the manual page for a list of possible returned error codes. After opening a catalog man:catgets[3] can be used to retrieve a message. The first parameter is the catalog identifier returned by man:catopen[3], the second one is the number of the set, the third one is the number of the messages, and the fourth one is a fallback message, which will be returned if the requested message cannot be retrieved from the catalog file. After using the catalog file, it must be closed by calling man:catclose[3], which has one argument, the catalog id. [[nls-example]] === A Practical Example The following example will demonstrate an easy solution on how to use NLS catalogs in a flexible way. The below lines need to be put into a common header file of the program, which is included into all source files where localized messages are necessary: [.programlisting] .... #ifdef WITHOUT_NLS #define getstr(n) nlsstr[n] #else #include nl_types.h extern nl_catd catalog; #define getstr(n) catgets(catalog, 1, n, nlsstr[n]) #endif extern char *nlsstr[]; .... Next, put these lines into the global declaration part of the main source file: [.programlisting] .... #ifndef WITHOUT_NLS #include nl_types.h nl_catd catalog; #endif /* * Default messages to use when NLS is disabled or no catalog * is found. */ char *nlsstr[] = { "", /* 1*/ "some random message", /* 2*/ "some other message" }; .... Next come the real code snippets, which open, read, and close the catalog: [.programlisting] .... #ifndef WITHOUT_NLS catalog = catopen("myapp", NL_CAT_LOCALE); #endif ... printf(getstr(1)); ... #ifndef WITHOUT_NLS catclose(catalog); #endif .... ==== Reducing Strings to Localize There is a good way of reducing the strings that need to be localized by using libc error messages. This is also useful to just avoid duplication and provide consistent error messages for the common errors that can be encountered by a great many of programs. First, here is an example that does not use libc error messages: [.programlisting] .... #include err.h ... if (!S_ISDIR(st.st_mode)) errx(1, "argument is not a directory"); .... This can be transformed to print an error message by reading `errno` and printing an error message accordingly: [.programlisting] .... #include err.h #include errno.h ... if (!S_ISDIR(st.st_mode)) { errno = ENOTDIR; err(1, NULL); } .... In this example, the custom string is eliminated, thus translators will have less work when localizing the program and users will see the usual "Not a directory" error message when they encounter this error. This message will probably seem more familiar to them. Please note that it was necessary to include [.filename]#errno.h# in order to directly access `errno`. It is worth to note that there are cases when `errno` is set automatically by a preceding call, so it is not necessary to set it explicitly: [.programlisting] .... #include err.h ... if ((p = malloc(size)) == NULL) err(1, NULL); .... [[nls-mk]] === Making use of [.filename]#bsd.nls.mk# Using the catalog files requires few repeatable steps, such as compiling the catalogs and installing them to the proper location. In order to simplify this process even more, [.filename]#bsd.nls.mk# introduces some macros. It is not necessary to include [.filename]#bsd.nls.mk# explicitly, it is pulled in from the common Makefiles, such as [.filename]#bsd.prog.mk# or [.filename]#bsd.lib.mk#. Usually it is enough to define `NLSNAME`, which should have the catalog name mentioned as the first argument of man:catopen[3] and list the catalog files in `NLS` without their `.msg` extension. Here is an example, which makes it possible to to disable NLS when used with the code examples before. The `WITHOUT_NLS` man:make[1] variable has to be defined in order to build the program without NLS support. [.programlisting] .... .if !defined(WITHOUT_NLS) NLS= es_ES.ISO8859-1 NLS+= hu_HU.ISO8859-2 NLS+= pt_BR.ISO8859-1 .else CFLAGS+= -DWITHOUT_NLS .endif .... Conventionally, the catalog files are placed under the [.filename]#nls# subdirectory and this is the default behavior of [.filename]#bsd.nls.mk#. It is possible, though to override the location of the catalogs with the `NLSSRCDIR` man:make[1] variable. The default name of the precompiled catalog files also follow the naming convention mentioned before. It can be overridden by setting the `NLSNAME` variable. There are other options to fine tune the processing of the catalog files but usually it is not needed, thus they are not described here. For further information on [.filename]#bsd.nls.mk#, please refer to the file itself, it is short and easy to understand. diff --git a/documentation/content/en/books/developers-handbook/tools/_index.adoc b/documentation/content/en/books/developers-handbook/tools/_index.adoc index 1565cc48e6..f9ff8200f6 100644 --- a/documentation/content/en/books/developers-handbook/tools/_index.adoc +++ b/documentation/content/en/books/developers-handbook/tools/_index.adoc @@ -1,1494 +1,1494 @@ --- title: Chapter 2. Programming Tools authors: - author: James Raynard - author: Murray Stokely prev: books/developers-handbook/introduction next: books/developers-handbook/secure description: Programming Tools tags: ["tools", "Interpreters", "Compilers", "cc", "make", "Debugging", "lldb", "gdb", "Emacs"] --- [[tools]] = Programming Tools :doctype: book :toc: macro :toclevels: 1 :icons: font :sectnums: :sectnumlevels: 6 :source-highlighter: rouge :experimental: :skip-front-matter: :xrefstyle: basic :relfileprefix: ../ :outfilesuffix: :sectnumoffset: 2 :c-plus-plus-command: c++ :clang-plus-plus-command: clang++ include::shared/mirrors.adoc[] include::shared/authors.adoc[] include::shared/releases.adoc[] include::shared/en/mailing-lists.adoc[] include::shared/en/teams.adoc[] include::shared/en/urls.adoc[] toc::[] [[tools-synopsis]] == Synopsis This chapter is an introduction to using some of the programming tools supplied with FreeBSD, although much of it will be applicable to many other versions of UNIX(R). It does _not_ attempt to describe coding in any detail. Most of the chapter assumes little or no previous programming knowledge, although it is hoped that most programmers will find something of value in it. [[tools-intro]] == Introduction FreeBSD offers an excellent development environment. Compilers for C and C++ and an assembler come with the basic system, not to mention classic UNIX(R) tools such as `sed` and `awk`. If that is not enough, there are many more compilers and interpreters in the Ports collection. The following section, <>, lists some of the available options. FreeBSD is very compatible with standards such as POSIX(R) and ANSI C, as well with its own BSD heritage, so it is possible to write applications that will compile and run with little or no modification on a wide range of platforms. However, all this power can be rather overwhelming at first if you have never written programs on a UNIX(R) platform before. This document aims to help you get up and running, without getting too deeply into more advanced topics. The intention is that this document should give you enough of the basics to be able to make some sense of the documentation. Most of the document requires little or no knowledge of programming, although it does assume a basic competence with using UNIX(R) and a willingness to learn! [[tools-programming]] == Introduction to Programming A program is a set of instructions that tell the computer to do various things; sometimes the instruction it has to perform depends on what happened when it performed a previous instruction. This section gives an overview of the two main ways in which you can give these instructions, or "commands" as they are usually called. One way uses an _interpreter_, the other a _compiler_. As human languages are too difficult for a computer to understand in an unambiguous way, commands are usually written in one or other languages specially designed for the purpose. === Interpreters With an interpreter, the language comes as an environment, where you type in commands at a prompt and the environment executes them for you. For more complicated programs, you can type the commands into a file and get the interpreter to load the file and execute the commands in it. If anything goes wrong, many interpreters will drop you into a debugger to help you track down the problem. The advantage of this is that you can see the results of your commands immediately, and mistakes can be corrected readily. The biggest disadvantage comes when you want to share your programs with someone. They must have the same interpreter, or you must have some way of giving it to them, and they need to understand how to use it. Also users may not appreciate being thrown into a debugger if they press the wrong key! From a performance point of view, interpreters can use up a lot of memory, and generally do not generate code as efficiently as compilers. In my opinion, interpreted languages are the best way to start if you have not done any programming before. This kind of environment is typically found with languages like Lisp, Smalltalk, Perl and Basic. It could also be argued that the UNIX(R) shell (`sh`, `csh`) is itself an interpreter, and many people do in fact write shell "scripts" to help with various "housekeeping" tasks on their machine. Indeed, part of the original UNIX(R) philosophy was to provide lots of small utility programs that could be linked together in shell scripts to perform useful tasks. === Interpreters Available with FreeBSD Here is a list of interpreters that are available from the FreeBSD Ports Collection, with a brief discussion of some of the more popular interpreted languages. Instructions on how to get and install applications from the Ports Collection can be found in the link:{handbook}#ports-using/[Ports section] of the handbook. BASIC:: Short for Beginner's All-purpose Symbolic Instruction Code. Developed in the 1950s for teaching University students to program and provided with every self-respecting personal computer in the 1980s, BASIC has been the first programming language for many programmers. It is also the foundation for Visual Basic. + The Bywater Basic Interpreter can be found in the Ports Collection as package:lang/bwbasic[] and the Phil Cockroft's Basic Interpreter (formerly Rabbit Basic) is available as package:lang/pbasic[]. Lisp:: A language that was developed in the late 1950s as an alternative to the "number-crunching" languages that were popular at the time. Instead of being based on numbers, Lisp is based on lists; in fact, the name is short for "List Processing". It is very popular in AI (Artificial Intelligence) circles. + Lisp is an extremely powerful and sophisticated language, but can be rather large and unwieldy. + Various implementations of Lisp that can run on UNIX(R) systems are available in the Ports Collection for FreeBSD. GNU Common Lisp can be found as package:lang/gcl[]. CLISP by Bruno Haible and Michael Stoll is available as package:lang/clisp[]. For CMUCL, which includes a highly-optimizing compiler too, or simpler Lisp implementations like SLisp, which implements most of the Common Lisp constructs in a few hundred lines of C code, package:lang/cmucl[] and package:lang/slisp[] are available respectively. Perl:: Very popular with system administrators for writing scripts; also often used on World Wide Web servers for writing CGI scripts. + Perl is available in the Ports Collection as package:lang/perl5.24[] for all FreeBSD releases. Scheme:: A dialect of Lisp that is rather more compact and cleaner than Common Lisp. Popular in Universities as it is simple enough to teach to undergraduates as a first language, while it has a high enough level of abstraction to be used in research work. + Scheme is available from the Ports Collection as package:lang/elk[] for the Elk Scheme Interpreter. The MIT Scheme Interpreter can be found in package:lang/mit-scheme[] and the SCM Scheme Interpreter in package:lang/scm[]. Icon:: Icon is a high-level language with extensive facilities for processing strings and structures. The version of Icon for FreeBSD can be found in the Ports Collection as package:lang/icon[]. Logo:: Logo is a language that is easy to learn, and has been used as an introductory programming language in various courses. It is an excellent tool to work with when teaching programming to smaller age groups, as it makes creation of elaborate geometric shapes an easy task. + The latest version of Logo for FreeBSD is available from the Ports Collection in package:lang/logo[]. Python:: Python is an Object-Oriented, interpreted language. Its advocates argue that it is one of the best languages to start programming with, since it is relatively easy to start with, but is not limited in comparison to other popular interpreted languages that are used for the development of large, complex applications (Perl and Tcl are two other languages that are popular for such tasks). + The latest version of Python is available from the Ports Collection in package:lang/python[]. Ruby:: Ruby is an interpreter, pure object-oriented programming language. It has become widely popular because of its easy to understand syntax, flexibility when writing code, and the ability to easily develop and maintain large, complex programs. + Ruby is available from the Ports Collection as package:lang/ruby25[]. Tcl and Tk:: Tcl is an embeddable, interpreted language, that has become widely used and became popular mostly because of its portability to many platforms. It can be used both for quickly writing small, prototype applications, or (when combined with Tk, a GUI toolkit) fully-fledged, featureful programs. + Various versions of Tcl are available as ports for FreeBSD. The latest version, Tcl 8.5, can be found in package:lang/tcl87[]. === Compilers Compilers are rather different. First of all, you write your code in a file (or files) using an editor. You then run the compiler and see if it accepts your program. If it did not compile, grit your teeth and go back to the editor; if it did compile and gave you a program, you can run it either at a shell command prompt or in a debugger to see if it works properly.footnote:[If you run it in the shell, you may get a core dump.] Obviously, this is not quite as direct as using an interpreter. However it allows you to do a lot of things which are very difficult or even impossible with an interpreter, such as writing code which interacts closely with the operating system-or even writing your own operating system! It is also useful if you need to write very efficient code, as the compiler can take its time and optimize the code, which would not be acceptable in an interpreter. Moreover, distributing a program written for a compiler is usually more straightforward than one written for an interpreter-you can just give them a copy of the executable, assuming they have the same operating system as you. As the edit-compile-run-debug cycle is rather tedious when using separate programs, many commercial compiler makers have produced Integrated Development Environments (IDEs for short). FreeBSD does not include an IDE in the base system, but package:devel/kdevelop[] is available in the Ports Collection and many use Emacs for this purpose. Using Emacs as an IDE is discussed in <>. [[tools-compiling]] == Compiling with `cc` This section deals with the gcc and clang compilers for C and C++, since they come with the FreeBSD base system. Starting with FreeBSD 10.X `clang` is installed as `cc`. The details of producing a program with an interpreter vary considerably between interpreters, and are usually well covered in the documentation and on-line help for the interpreter. Once you have written your masterpiece, the next step is to convert it into something that will (hopefully!) run on FreeBSD. This usually involves several steps, each of which is done by a separate program. [.procedure] . Pre-process your source code to remove comments and do other tricks like expanding macros in C. . Check the syntax of your code to see if you have obeyed the rules of the language. If you have not, it will complain! . Convert the source code into assembly language-this is very close to machine code, but still understandable by humans. Allegedly. . Convert the assembly language into machine code-yep, we are talking bits and bytes, ones and zeros here. . Check that you have used things like functions and global variables in a consistent way. For example, if you have called a non-existent function, it will complain. . If you are trying to produce an executable from several source code files, work out how to fit them all together. . Work out how to produce something that the system's run-time loader will be able to load into memory and run. . Finally, write the executable on the filesystem. The word _compiling_ is often used to refer to just steps 1 to 4-the others are referred to as _linking_. Sometimes step 1 is referred to as _pre-processing_ and steps 3-4 as _assembling_. Fortunately, almost all this detail is hidden from you, as `cc` is a front end that manages calling all these programs with the right arguments for you; simply typing [source,bash] .... % cc foobar.c .... will cause [.filename]#foobar.c# to be compiled by all the steps above. If you have more than one file to compile, just do something like [source,bash] .... % cc foo.c bar.c .... Note that the syntax checking is just that-checking the syntax. It will not check for any logical mistakes you may have made, like putting the program into an infinite loop, or using a bubble sort when you meant to use a binary sort.footnote:[In case you did not know, a binary sort is an efficient way of sorting things into order and a bubble sort is not.] There are lots and lots of options for `cc`, which are all in the manual page. Here are a few of the most important ones, with examples of how to use them. `-o _filename_`:: The output name of the file. If you do not use this option, `cc` will produce an executable called [.filename]#a.out#.footnote:[The reasons for this are buried in the mists of history.] + [source,bash] .... % cc foobar.c executable is a.out % cc -o foobar foobar.c executable is foobar .... `-c`:: Just compile the file, do not link it. Useful for toy programs where you just want to check the syntax, or if you are using a [.filename]#Makefile#. + [source,bash] .... % cc -c foobar.c .... + This will produce an _object file_ (not an executable) called [.filename]#foobar.o#. This can be linked together with other object files into an executable. `-g`:: Create a debug version of the executable. This makes the compiler put information into the executable about which line of which source file corresponds to which function call. A debugger can use this information to show the source code as you step through the program, which is _very_ useful; the disadvantage is that all this extra information makes the program much bigger. Normally, you compile with `-g` while you are developing a program and then compile a "release version" without `-g` when you are satisfied it works properly. + [source,bash] .... % cc -g foobar.c .... + This will produce a debug version of the program. footnote:[Note, we did not use the -o flag to specify the executable name, so we will get an executable called a.out. Producing a debug version called foobar is left as an exercise for the reader!] `-O`:: Create an optimized version of the executable. The compiler performs various clever tricks to try to produce an executable that runs faster than normal. You can add a number after the `-O` to specify a higher level of optimization, but this often exposes bugs in the compiler's optimizer. + [source,bash] .... % cc -O -o foobar foobar.c .... + This will produce an optimized version of [.filename]#foobar#. The following three flags will force `cc` to check that your code complies to the relevant international standard, often referred to as the ANSI standard, though strictly speaking it is an ISO standard. `-Wall`:: Enable all the warnings which the authors of `cc` believe are worthwhile. Despite the name, it will not enable all the warnings `cc` is capable of. `-ansi`:: Turn off most, but not all, of the non-ANSI C features provided by `cc`. Despite the name, it does not guarantee strictly that your code will comply to the standard. `-pedantic`:: Turn off _all_ ``cc``'s non-ANSI C features. Without these flags, `cc` will allow you to use some of its non-standard extensions to the standard. Some of these are very useful, but will not work with other compilers-in fact, one of the main aims of the standard is to allow people to write code that will work with any compiler on any system. This is known as _portable code_. Generally, you should try to make your code as portable as possible, as otherwise you may have to completely rewrite the program later to get it to work somewhere else-and who knows what you may be using in a few years time? [source,bash] .... % cc -Wall -ansi -pedantic -o foobar foobar.c .... This will produce an executable [.filename]#foobar# after checking [.filename]#foobar.c# for standard compliance. `-l__library__`:: Specify a function library to be used at link time. + The most common example of this is when compiling a program that uses some of the mathematical functions in C. Unlike most other platforms, these are in a separate library from the standard C one and you have to tell the compiler to add it. + The rule is that if the library is called [.filename]#libsomething.a#, you give `cc` the argument `-l__something__`. For example, the math library is [.filename]#libm.a#, so you give `cc` the argument `-lm`. A common "gotcha" with the math library is that it has to be the last library on the command line. + [source,bash] .... % cc -o foobar foobar.c -lm .... + This will link the math library functions into [.filename]#foobar#. + If you are compiling C++ code, use {c-plus-plus-command}. {c-plus-plus-command} can also be invoked as {clang-plus-plus-command} on FreeBSD. + [source,bash] .... % c++ -o foobar foobar.cc .... + This will both produce an executable [.filename]#foobar# from the C++ source file [.filename]#foobar.cc#. === Common `cc` Queries and Problems ==== I am trying to write a program which uses the sin() function and I get an error like this. What does it mean? [source,bash] .... /var/tmp/cc0143941.o: Undefined symbol `_sin' referenced from text segment .... When using mathematical functions like `sin()`, you have to tell `cc` to link in the math library, like so: [source,bash] .... % cc -o foobar foobar.c -lm .... ==== All right, I wrote this simple program to practice using -lm. All it does is raise 2.1 to the power of 6. [.programlisting] .... #include int main() { float f; f = pow(2.1, 6); printf("2.1 ^ 6 = %f\n", f); return 0; } .... and I compiled it as: [source,bash] .... % cc temp.c -lm .... like you said I should, but I get this when I run it: [source,bash] .... % ./a.out 2.1 ^ 6 = 1023.000000 .... This is not the right answer! What is going on? When the compiler sees you call a function, it checks if it has already seen a prototype for it. If it has not, it assumes the function returns an int, which is definitely not what you want here. ==== So how do I fix this? The prototypes for the mathematical functions are in [.filename]#math.h#. If you include this file, the compiler will be able to find the prototype and it will stop doing strange things to your calculation! [.programlisting] .... #include #include int main() { ... .... After recompiling it as you did before, run it: [source,bash] .... % ./a.out 2.1 ^ 6 = 85.766121 .... If you are using any of the mathematical functions, _always_ include [.filename]#math.h# and remember to link in the math library. ==== I compiled a file called foobar.c and I cannot find an executable called foobar. Where has it gone? Remember, `cc` will call the executable [.filename]#a.out# unless you tell it differently. Use the `-o _filename_` option: [source,bash] .... % cc -o foobar foobar.c .... ==== OK, I have an executable called foobar, I can see it when I run ls, but when I type in foobar at the command prompt it tells me there is no such file. Why can it not find it? Unlike MS-DOS(R), UNIX(R) does not look in the current directory when it is trying to find out which executable you want it to run, unless you tell it to. Type `./foobar`, which means "run the file called [.filename]#foobar# in the current directory." === I called my executable test, but nothing happens when I run it. What is going on? Most UNIX(R) systems have a program called `test` in [.filename]#/usr/bin# and the shell is picking that one up before it gets to checking the current directory. Either type: [source,bash] .... % ./test .... or choose a better name for your program! ==== I compiled my program and it seemed to run all right at first, then there was an error and it said something about core dumped. What does that mean? The name _core dump_ dates back to the very early days of UNIX(R), when the machines used core memory for storing data. Basically, if the program failed under certain conditions, the system would write the contents of core memory to disk in a file called [.filename]#core#, which the programmer could then pore over to find out what went wrong. ==== Fascinating stuff, but what I am supposed to do now? Use a debugger to analyze the core (see <>). ==== When my program dumped core, it said something about a segmentation fault. What is that? This basically means that your program tried to perform some sort of illegal operation on memory; UNIX(R) is designed to protect the operating system and other programs from rogue programs. Common causes for this are: * Trying to write to a NULL pointer, eg + [.programlisting] .... char *foo = NULL; strcpy(foo, "bang!"); .... * Using a pointer that has not been initialized, eg + [.programlisting] .... char *foo; strcpy(foo, "bang!"); .... + The pointer will have some random value that, with luck, will point into an area of memory that is not available to your program and the kernel will kill your program before it can do any damage. If you are unlucky, it will point somewhere inside your own program and corrupt one of your data structures, causing the program to fail mysteriously. * Trying to access past the end of an array, eg + [.programlisting] .... int bar[20]; bar[27] = 6; .... * Trying to store something in read-only memory, eg + [.programlisting] .... char *foo = "My string"; strcpy(foo, "bang!"); .... + UNIX(R) compilers often put string literals like `"My string"` into read-only areas of memory. * Doing naughty things with `malloc()` and `free()`, eg + [.programlisting] .... char bar[80]; free(bar); .... + or + [.programlisting] .... char *foo = malloc(27); free(foo); free(foo); .... Making one of these mistakes will not always lead to an error, but they are always bad practice. Some systems and compilers are more tolerant than others, which is why programs that ran well on one system can crash when you try them on an another. ==== Sometimes when I get a core dump it says bus error. It says in my UNIX(R) book that this means a hardware problem, but the computer still seems to be working. Is this true? No, fortunately not (unless of course you really do have a hardware problem...). This is usually another way of saying that you accessed memory in a way you should not have. ==== This dumping core business sounds as though it could be quite useful, if I can make it happen when I want to. Can I do this, or do I have to wait until there is an error? Yes, just go to another console or xterm, do [source,bash] .... % ps .... to find out the process ID of your program, and do [source,bash] .... % kill -ABRT pid .... where `_pid_` is the process ID you looked up. This is useful if your program has got stuck in an infinite loop, for instance. If your program happens to trap SIGABRT, there are several other signals which have a similar effect. Alternatively, you can create a core dump from inside your program, by calling the `abort()` function. See the manual page of man:abort[3] to learn more. If you want to create a core dump from outside your program, but do not want the process to terminate, you can use the `gcore` program. See the manual page of man:gcore[1] for more information. [[tools-make]] == Make === What is `make`? When you are working on a simple program with only one or two source files, typing in [source,bash] .... % cc file1.c file2.c .... is not too bad, but it quickly becomes very tedious when there are several files-and it can take a while to compile, too. One way to get around this is to use object files and only recompile the source file if the source code has changed. So we could have something like: [source,bash] .... % cc file1.o file2.o … file37.c … .... if we had changed [.filename]#file37.c#, but not any of the others, since the last time we compiled. This may speed up the compilation quite a bit, but does not solve the typing problem. Or we could write a shell script to solve the typing problem, but it would have to re-compile everything, making it very inefficient on a large project. What happens if we have hundreds of source files lying about? What if we are working in a team with other people who forget to tell us when they have changed one of their source files that we use? Perhaps we could put the two solutions together and write something like a shell script that would contain some kind of magic rule saying when a source file needs compiling. Now all we need now is a program that can understand these rules, as it is a bit too complicated for the shell. This program is called `make`. It reads in a file, called a _makefile_, that tells it how different files depend on each other, and works out which files need to be re-compiled and which ones do not. For example, a rule could say something like "if [.filename]#fromboz.o# is older than [.filename]#fromboz.c#, that means someone must have changed [.filename]#fromboz.c#, so it needs to be re-compiled." The makefile also has rules telling make _how_ to re-compile the source file, making it a much more powerful tool. Makefiles are typically kept in the same directory as the source they apply to, and can be called [.filename]#makefile#, [.filename]#Makefile# or [.filename]#MAKEFILE#. Most programmers use the name [.filename]#Makefile#, as this puts it near the top of a directory listing, where it can easily be seen.footnote:[They do not use the MAKEFILE form as block capitals are often used for documentation files like README.] === Example of Using `make` Here is a very simple make file: [.programlisting] .... foo: foo.c cc -o foo foo.c .... It consists of two lines, a dependency line and a creation line. The dependency line here consists of the name of the program (known as the _target_), followed by a colon, then whitespace, then the name of the source file. When `make` reads this line, it looks to see if [.filename]#foo# exists; if it exists, it compares the time [.filename]#foo# was last modified to the time [.filename]#foo.c# was last modified. If [.filename]#foo# does not exist, or is older than [.filename]#foo.c#, it then looks at the creation line to find out what to do. In other words, this is the rule for working out when [.filename]#foo.c# needs to be re-compiled. The creation line starts with a tab (press kbd:[tab]) and then the command you would type to create [.filename]#foo# if you were doing it at a command prompt. If [.filename]#foo# is out of date, or does not exist, `make` then executes this command to create it. In other words, this is the rule which tells make how to re-compile [.filename]#foo.c#. So, when you type `make`, it will make sure that [.filename]#foo# is up to date with respect to your latest changes to [.filename]#foo.c#. This principle can be extended to [.filename]#Makefile#'s with hundreds of targets-in fact, on FreeBSD, it is possible to compile the entire operating system just by typing `make world` in the appropriate directory! Another useful property of makefiles is that the targets do not have to be programs. For instance, we could have a make file that looks like this: [.programlisting] .... foo: foo.c cc -o foo foo.c install: cp foo /home/me .... We can tell make which target we want to make by typing: [source,bash] .... % make target .... `make` will then only look at that target and ignore any others. For example, if we type `make foo` with the makefile above, make will ignore the `install` target. If we just type `make` on its own, make will always look at the first target and then stop without looking at any others. So if we typed `make` here, it will just go to the `foo` target, re-compile [.filename]#foo# if necessary, and then stop without going on to the `install` target. Notice that the `install` target does not actually depend on anything! This means that the command on the following line is always executed when we try to make that target by typing `make install`. In this case, it will copy [.filename]#foo# into the user's home directory. This is often used by application makefiles, so that the application can be installed in the correct directory when it has been correctly compiled. This is a slightly confusing subject to try to explain. If you do not quite understand how `make` works, the best thing to do is to write a simple program like "hello world" and a make file like the one above and experiment. Then progress to using more than one source file, or having the source file include a header file. `touch` is very useful here-it changes the date on a file without you having to edit it. === Make and include-files C code often starts with a list of files to include, for example stdio.h. Some of these files are system-include files, some of them are from the project you are now working on: [.programlisting] .... #include #include "foo.h" int main(.... .... To make sure that this file is recompiled the moment [.filename]#foo.h# is changed, you have to add it in your [.filename]#Makefile#: [.programlisting] .... foo: foo.c foo.h .... The moment your project is getting bigger and you have more and more own include-files to maintain, it will be a pain to keep track of all include files and the files which are depending on it. If you change an include-file but forget to recompile all the files which are depending on it, the results will be devastating. `clang` has an option to analyze your files and to produce a list of include-files and their dependencies: `-MM`. If you add this to your Makefile: [.programlisting] .... depend: cc -E -MM *.c > .depend .... and run `make depend`, the file [.filename]#.depend# will appear with a list of object-files, C-files and the include-files: [.programlisting] .... foo.o: foo.c foo.h .... If you change [.filename]#foo.h#, next time you run `make` all files depending on [.filename]#foo.h# will be recompiled. Do not forget to run `make depend` each time you add an include-file to one of your files. === FreeBSD Makefiles Makefiles can be rather complicated to write. Fortunately, BSD-based systems like FreeBSD come with some very powerful ones as part of the system. One very good example of this is the FreeBSD ports system. Here is the essential part of a typical ports [.filename]#Makefile#: [.programlisting] .... MASTER_SITES= ftp://freefall.cdrom.com/pub/FreeBSD/LOCAL_PORTS/ DISTFILES= scheme-microcode+dist-7.3-freebsd.tgz .include .... Now, if we go to the directory for this port and type `make`, the following happens: [.procedure] . A check is made to see if the source code for this port is already on the system. . If it is not, an FTP connection to the URL in MASTER_SITES is set up to download the source. . The checksum for the source is calculated and compared it with one for a known, good, copy of the source. This is to make sure that the source was not corrupted while in transit. . Any changes required to make the source work on FreeBSD are applied-this is known as _patching_. . Any special configuration needed for the source is done. (Many UNIX(R) program distributions try to work out which version of UNIX(R) they are being compiled on and which optional UNIX(R) features are present-this is where they are given the information in the FreeBSD ports scenario). . The source code for the program is compiled. In effect, we change to the directory where the source was unpacked and do `make`-the program's own make file has the necessary information to build the program. . We now have a compiled version of the program. If we wish, we can test it now; when we feel confident about the program, we can type `make install`. This will cause the program and any supporting files it needs to be copied into the correct location; an entry is also made into a `package database`, so that the port can easily be uninstalled later if we change our mind about it. Now I think you will agree that is rather impressive for a four line script! The secret lies in the last line, which tells `make` to look in the system makefile called [.filename]#bsd.port.mk#. It is easy to overlook this line, but this is where all the clever stuff comes from-someone has written a makefile that tells `make` to do all the things above (plus a couple of other things I did not mention, including handling any errors that may occur) and anyone can get access to that just by putting a single line in their own make file! -If you want to have a look at these system makefiles, they are in [.filename]#/usr/shared/mk#, but it is probably best to wait until you have had a bit of practice with makefiles, as they are very complicated (and if you do look at them, make sure you have a flask of strong coffee handy!) +If you want to have a look at these system makefiles, they are in [.filename]#/usr/share/mk#, but it is probably best to wait until you have had a bit of practice with makefiles, as they are very complicated (and if you do look at them, make sure you have a flask of strong coffee handy!) === More Advanced Uses of `make` `Make` is a very powerful tool, and can do much more than the simple example above shows. Unfortunately, there are several different versions of `make`, and they all differ considerably. The best way to learn what they can do is probably to read the documentation-hopefully this introduction will have given you a base from which you can do this. -The version of make that comes with FreeBSD is the Berkeley make; there is a tutorial for it in [.filename]#/usr/shared/doc/psd/12.make#. To view it, do +The version of make that comes with FreeBSD is the Berkeley make; there is a tutorial for it in [.filename]#/usr/share/doc/psd/12.make#. To view it, do [source,bash] .... % zmore paper.ascii.gz .... in that directory. Many applications in the ports use GNU make, which has a very good set of "info" pages. If you have installed any of these ports, GNU make will automatically have been installed as `gmake`. It is also available as a port and package in its own right. To view the info pages for GNU make, you will have to edit [.filename]#dir# in the [.filename]#/usr/local/info# directory to add an entry for it. This involves adding a line like [.programlisting] .... * Make: (make). The GNU Make utility. .... to the file. Once you have done this, you can type `info` and then select [.guimenuitem]#make# from the menu (or in Emacs, do `C-h i`). [[debugging]] == Debugging === Introduction to Available Debuggers Using a debugger allows running the program under more controlled circumstances. Typically, it is possible to step through the program a line at a time, inspect the value of variables, change them, tell the debugger to run up to a certain point and then stop, and so on. It is also possible to attach to a program that is already running, or load a core file to investigate why the program crashed. It is even possible to debug the kernel, though that is a little trickier than the user applications we will be discussing in this section. This section is intended to be a quick introduction to using debuggers and does not cover specialized topics such as debugging the kernel. For more information about that, refer to crossref:kerneldebug[kerneldebug,Kernel Debugging]. The standard debugger supplied with FreeBSD {rel121-current} is called `lldb` (LLVM debugger). As it is part of the standard installation for that release, there is no need to do anything special to use it. It has good command help, accessible via the `help` command, as well as https://lldb.llvm.org/[a web tutorial and documentation]. [NOTE] ==== The `lldb` command is available for FreeBSD {rel113-current} link:{handbook}#ports-using/[from ports or packages] as package:devel/llvm[]. This will install the default version of lldb (currently 9.0). ==== The other debugger available with FreeBSD is called `gdb` (GNU debugger). Unlike lldb, it is not installed by default on FreeBSD {rel121-current}; to use it, link:{handbook}#ports-using/[install] package:devel/gdb[] from ports or packages. The version installed by default on FreeBSD {rel113-current} is old; instead, install package:devel/gdb[] there as well. It has quite good on-line help, as well as a set of info pages. Which one to use is largely a matter of taste. If familiar with one only, use that one. People familiar with neither or both but wanting to use one from inside Emacs will need to use `gdb` as `lldb` is unsupported by Emacs. Otherwise, try both and see which one you prefer. === Using lldb ==== Starting lldb Start up lldb by typing [source,bash] .... % lldb -- progname .... ==== Running a Program with lldb Compile the program with `-g` to get the most out of using `lldb`. It will work without, but will only display the name of the function currently running, instead of the source code. If it displays a line like: [source,bash] .... Breakpoint 1: where = temp`main, address = … .... (without an indication of source code filename and line number) when setting a breakpoint, this means that the program was not compiled with `-g`. [TIP] ==== Most `lldb` commands have shorter forms that can be used instead. The longer forms are used here for clarity. ==== At the `lldb` prompt, type `breakpoint set -n main`. This will tell the debugger not to display the preliminary set-up code in the program being run and to stop execution at the beginning of the program's code. Now type `process launch` to actually start the program- it will start at the beginning of the set-up code and then get stopped by the debugger when it calls `main()`. To step through the program a line at a time, type `thread step-over`. When the program gets to a function call, step into it by typing `thread step-in`. Once in a function call, return from it by typing `thread step-out` or use `up` and `down` to take a quick look at the caller. Here is a simple example of how to spot a mistake in a program with `lldb`. This is our program (with a deliberate mistake): [.programlisting] .... #include int bazz(int anint); main() { int i; printf("This is my program\n"); bazz(i); return 0; } int bazz(int anint) { printf("You gave me %d\n", anint); return anint; } .... This program sets i to be `5` and passes it to a function `bazz()` which prints out the number we gave it. Compiling and running the program displays [source,bash] .... % cc -g -o temp temp.c % ./temp This is my program anint = -5360 .... That is not what was expected! Time to see what is going on! [source,bash] .... % lldb -- temp (lldb) target create "temp" Current executable set to 'temp' (x86_64). (lldb) breakpoint set -n main Skip the set-up code Breakpoint 1: where = temp`main + 15 at temp.c:8:2, address = 0x00000000002012ef lldb puts breakpoint at main() (lldb) process launch Run as far as main() Process 9992 launching Process 9992 launched: '/home/pauamma/tmp/temp' (x86_64) Program starts running Process 9992 stopped * thread #1, name = 'temp', stop reason = breakpoint 1.1 lldb stops at main() frame #0: 0x00000000002012ef temp`main at temp.c:8:2 5 main() { 6 int i; 7 -> 8 printf("This is my program\n"); Indicates the line where it stopped 9 bazz(i); 10 return 0; 11 } (lldb) thread step-over Go to next line This is my program Program prints out Process 9992 stopped * thread #1, name = 'temp', stop reason = step over frame #0: 0x0000000000201300 temp`main at temp.c:9:7 6 int i; 7 8 printf("This is my program\n"); -> 9 bazz(i); 10 return 0; 11 } 12 (lldb) thread step-in step into bazz() Process 9992 stopped * thread #1, name = 'temp', stop reason = step in frame #0: 0x000000000020132b temp`bazz(anint=-5360) at temp.c:14:29 lldb displays stack frame 11 } 12 13 int bazz(int anint) { -> 14 printf("You gave me %d\n", anint); 15 return anint; 16 } (lldb) .... Hang on a minute! How did anint get to be `-5360`? Was it not set to `5` in `main()`? Let us move up to `main()` and have a look. [source,bash] .... (lldb) up Move up call stack frame #1: 0x000000000020130b temp`main at temp.c:9:2 lldb displays stack frame 6 int i; 7 8 printf("This is my program\n"); -> 9 bazz(i); 10 return 0; 11 } 12 (lldb) frame variable i Show us the value of i (int) i = -5360 lldb displays -5360 .... Oh dear! Looking at the code, we forgot to initialize i. We meant to put [.programlisting] .... ... main() { int i; i = 5; printf("This is my program\n"); ... .... but we left the `i=5;` line out. As we did not initialize i, it had whatever number happened to be in that area of memory when the program ran, which in this case happened to be `-5360`. [NOTE] ==== The `lldb` command displays the stack frame every time we go into or out of a function, even if we are using `up` and `down` to move around the call stack. This shows the name of the function and the values of its arguments, which helps us keep track of where we are and what is going on. (The stack is a storage area where the program stores information about the arguments passed to functions and where to go when it returns from a function call.) ==== ==== Examining a Core File with lldb A core file is basically a file which contains the complete state of the process when it crashed. In "the good old days", programmers had to print out hex listings of core files and sweat over machine code manuals, but now life is a bit easier. Incidentally, under FreeBSD and other 4.4BSD systems, a core file is called [.filename]#progname.core# instead of just [.filename]#core#, to make it clearer which program a core file belongs to. To examine a core file, specify the name of the core file in addition to the program itself. Instead of starting up `lldb` in the usual way, type `lldb -c _progname_.core -- _progname_` The debugger will display something like this: [source,bash,subs="verbatim,quotes"] .... % lldb -c [.filename]#progname.core# -- [.filename]#progname# (lldb) target create "[.filename]#progname#" --core "[.filename]#progname#.core" Core file '/home/pauamma/tmp/[.filename]#progname.core#' (x86_64) was loaded. (lldb) .... In this case, the program was called [.filename]#progname#, so the core file is called [.filename]#progname.core#. The debugger does not display why the program crashed or where. For this, use `thread backtrace all`. This will also show how the function where the program dumped core was called. [source,bash,subs="verbatim,quotes"] .... (lldb) thread backtrace all * thread #1, name = 'progname', stop reason = signal SIGSEGV * frame #0: 0x0000000000201347 progname`bazz(anint=5) at temp2.c:17:10 frame #1: 0x0000000000201312 progname`main at temp2.c:10:2 frame #2: 0x000000000020110f progname`_start(ap=, cleanup=) at crt1.c:76:7 (lldb) .... `SIGSEGV` indicates that the program tried to access memory (run code or read/write data usually) at a location that does not belong to it, but does not give any specifics. For that, look at the source code at line 10 of file temp2.c, in `bazz()`. The backtrace also says that in this case, `bazz()` was called from `main()`. ==== Attaching to a Running Program with lldb One of the neatest features about `lldb` is that it can attach to a program that is already running. Of course, that requires sufficient permissions to do so. A common problem is stepping through a program that forks and wanting to trace the child, but the debugger will only trace the parent. To do that, start up another `lldb`, use `ps` to find the process ID for the child, and do [source,bash] .... (lldb) process attach -p pid .... in `lldb`, and then debug as usual. For that to work well, the code that calls `fork` to create the child needs to do something like the following (courtesy of the `gdb` info pages): [.programlisting] .... ... if ((pid = fork()) < 0) /* _Always_ check this */ error(); else if (pid == 0) { /* child */ int PauseMode = 1; while (PauseMode) sleep(10); /* Wait until someone attaches to us */ ... } else { /* parent */ ... .... Now all that is needed is to attach to the child, set PauseMode to `0` with `expr PauseMode = 0` and wait for the `sleep()` call to return. === Remote Debugging Using LLDB [NOTE] ==== The described functionality is available starting with LLDB version 12.0.0. Users of FreeBSD releases containing an earlier LLDB version may wish to use the snapshot available in link:{handbook}#ports-using/[ports or packages], as package:devel/llvm-devel[]. ==== Starting with LLDB 12.0.0, remote debugging is supported on FreeBSD. This means that `lldb-server` can be started to debug a program on one host, while the interactive `lldb` client connects to it from another one. To launch a new process to be debugged remotely, run `lldb-server` on the remote server by typing [source,bash] .... % lldb-server g host:port -- progname .... The process will be stopped immediately after launching, and `lldb-server` will wait for the client to connect. Start `lldb` locally and type the following command to connect to the remote server: [source,bash] .... (lldb) gdb-remote host:port .... `lldb-server` can also attach to a running process. To do that, type the following on the remote server: [source,bash] .... % lldb-server g host:port --attach pid-or-name .... === Using gdb ==== Starting gdb Start up gdb by typing [source,bash] .... % gdb progname .... although many people prefer to run it inside Emacs. To do this, type: [source,bash] .... M-x gdb RET progname RET .... Finally, for those finding its text-based command-prompt style off-putting, there is a graphical front-end for it (package:devel/xxgdb[]) in the Ports Collection. ==== Running a Program with gdb Compile the program with `-g` to get the most out of using `gdb`. It will work without, but will only display the name of the function currently running, instead of the source code. A line like: [source,bash] .... ... (no debugging symbols found) ... .... when `gdb` starts up means that the program was not compiled with `-g`. At the `gdb` prompt, type `break main`. This will tell the debugger to skip the preliminary set-up code in the program being run and to stop execution at the beginning of the program's code. Now type `run` to start the program- it will start at the beginning of the set-up code and then get stopped by the debugger when it calls `main()`. To step through the program a line at a time, press `n`. When at a function call, step into it by pressing `s`. Once in a function call, return from it by pressing `f`, or use `up` and `down` to take a quick look at the caller. Here is a simple example of how to spot a mistake in a program with `gdb`. This is our program (with a deliberate mistake): [.programlisting] .... #include int bazz(int anint); main() { int i; printf("This is my program\n"); bazz(i); return 0; } int bazz(int anint) { printf("You gave me %d\n", anint); return anint; } .... This program sets i to be `5` and passes it to a function `bazz()` which prints out the number we gave it. Compiling and running the program displays [source,bash] .... % cc -g -o temp temp.c % ./temp This is my program anint = 4231 .... That was not what we expected! Time to see what is going on! [source,bash] .... % gdb temp GDB is free software and you are welcome to distribute copies of it under certain conditions; type "show copying" to see the conditions. There is absolutely no warranty for GDB; type "show warranty" for details. GDB 4.13 (i386-unknown-freebsd), Copyright 1994 Free Software Foundation, Inc. (gdb) break main Skip the set-up code Breakpoint 1 at 0x160f: file temp.c, line 9. gdb puts breakpoint at main() (gdb) run Run as far as main() Starting program: /home/james/tmp/temp Program starts running Breakpoint 1, main () at temp.c:9 gdb stops at main() (gdb) n Go to next line This is my program Program prints out (gdb) s step into bazz() bazz (anint=4231) at temp.c:17 gdb displays stack frame (gdb) .... Hang on a minute! How did anint get to be `4231`? Was it not set to `5` in `main()`? Let us move up to `main()` and have a look. [source,bash] .... (gdb) up Move up call stack #1 0x1625 in main () at temp.c:11 gdb displays stack frame (gdb) p i Show us the value of i $1 = 4231 gdb displays 4231 .... Oh dear! Looking at the code, we forgot to initialize i. We meant to put [.programlisting] .... ... main() { int i; i = 5; printf("This is my program\n"); ... .... but we left the `i=5;` line out. As we did not initialize i, it had whatever number happened to be in that area of memory when the program ran, which in this case happened to be `4231`. [NOTE] ==== The `gdb` command displays the stack frame every time we go into or out of a function, even if we are using `up` and `down` to move around the call stack. This shows the name of the function and the values of its arguments, which helps us keep track of where we are and what is going on. (The stack is a storage area where the program stores information about the arguments passed to functions and where to go when it returns from a function call.) ==== ==== Examining a Core File with gdb A core file is basically a file which contains the complete state of the process when it crashed. In "the good old days", programmers had to print out hex listings of core files and sweat over machine code manuals, but now life is a bit easier. Incidentally, under FreeBSD and other 4.4BSD systems, a core file is called [.filename]#progname.core# instead of just [.filename]#core#, to make it clearer which program a core file belongs to. To examine a core file, start up `gdb` in the usual way. Instead of typing `break` or `run`, type [source,bash] .... (gdb) core progname.core .... If the core file is not in the current directory, type `dir /path/to/core/file` first. The debugger should display something like this: [source,bash,subs="verbatim,quotes"] .... % gdb [.filename]#progname# GDB is free software and you are welcome to distribute copies of it under certain conditions; type "show copying" to see the conditions. There is absolutely no warranty for GDB; type "show warranty" for details. GDB 4.13 (i386-unknown-freebsd), Copyright 1994 Free Software Foundation, Inc. (gdb) core [.filename]#progname.core# Core was generated by `[.filename]#progname#'. Program terminated with signal 11, Segmentation fault. Cannot access memory at address 0x7020796d. #0 0x164a in bazz (anint=0x5) at temp.c:17 (gdb) .... In this case, the program was called [.filename]#progname#, so the core file is called [.filename]#progname.core#. We can see that the program crashed due to trying to access an area in memory that was not available to it in a function called `bazz`. Sometimes it is useful to be able to see how a function was called, as the problem could have occurred a long way up the call stack in a complex program. `bt` causes `gdb` to print out a back-trace of the call stack: [source,bash] .... (gdb) bt #0 0x164a in bazz (anint=0x5) at temp.c:17 #1 0xefbfd888 in end () #2 0x162c in main () at temp.c:11 (gdb) .... The `end()` function is called when a program crashes; in this case, the `bazz()` function was called from `main()`. ==== Attaching to a Running Program with gdb One of the neatest features about `gdb` is that it can attach to a program that is already running. Of course, that requires sufficient permissions to do so. A common problem is stepping through a program that forks and wanting to trace the child, but the debugger will only trace the parent. To do that, start up another `gdb`, use `ps` to find the process ID for the child, and do [source,bash] .... (gdb) attach pid .... in `gdb`, and then debug as usual. For that to work well, the code that calls `fork` to create the child needs to do something like the following (courtesy of the `gdb` info pages): [.programlisting] .... ... if ((pid = fork()) < 0) /* _Always_ check this */ error(); else if (pid == 0) { /* child */ int PauseMode = 1; while (PauseMode) sleep(10); /* Wait until someone attaches to us */ ... } else { /* parent */ ... .... Now all that is needed is to attach to the child, set PauseMode to `0`, and wait for the `sleep()` call to return! [[emacs]] == Using Emacs as a Development Environment === Emacs Emacs is a highly customizable editor-indeed, it has been customized to the point where it is more like an operating system than an editor! Many developers and sysadmins do in fact spend practically all their time working inside Emacs, leaving it only to log out. It is impossible even to summarize everything Emacs can do here, but here are some of the features of interest to developers: * Very powerful editor, allowing search-and-replace on both strings and regular expressions (patterns), jumping to start/end of block expression, etc, etc. * Pull-down menus and online help. * Language-dependent syntax highlighting and indentation. * Completely customizable. * You can compile and debug programs within Emacs. * On a compilation error, you can jump to the offending line of source code. * Friendly-ish front-end to the `info` program used for reading GNU hypertext documentation, including the documentation on Emacs itself. * Friendly front-end to `gdb`, allowing you to look at the source code as you step through your program. And doubtless many more that have been overlooked. Emacs can be installed on FreeBSD using the package:editors/emacs[] port. Once it is installed, start it up and do `C-h t` to read an Emacs tutorial-that means hold down kbd:[control], press kbd:[h], let go of kbd:[control], and then press kbd:[t]. (Alternatively, you can use the mouse to select [.guimenuitem]#Emacs Tutorial# from the menu:Help[] menu.) Although Emacs does have menus, it is well worth learning the key bindings, as it is much quicker when you are editing something to press a couple of keys than to try to find the mouse and then click on the right place. And, when you are talking to seasoned Emacs users, you will find they often casually throw around expressions like "`M-x replace-s RET foo RET bar RET`" so it is useful to know what they mean. And in any case, Emacs has far too many useful functions for them to all fit on the menu bars. Fortunately, it is quite easy to pick up the key-bindings, as they are displayed next to the menu item. My advice is to use the menu item for, say, opening a file until you understand how it works and feel confident with it, then try doing C-x C-f. When you are happy with that, move on to another menu command. If you cannot remember what a particular combination of keys does, select [.guimenuitem]#Describe Key# from the menu:Help[] menu and type it in-Emacs will tell you what it does. You can also use the [.guimenuitem]#Command Apropos# menu item to find out all the commands which contain a particular word in them, with the key binding next to it. By the way, the expression above means hold down the kbd:[Meta] key, press kbd:[x], release the kbd:[Meta] key, type `replace-s` (short for `replace-string`-another feature of Emacs is that you can abbreviate commands), press the kbd:[return] key, type `foo` (the string you want replaced), press the kbd:[return] key, type bar (the string you want to replace `foo` with) and press kbd:[return] again. Emacs will then do the search-and-replace operation you have just requested. If you are wondering what on earth kbd:[Meta] is, it is a special key that many UNIX(R) workstations have. Unfortunately, PC's do not have one, so it is usually kbd:[alt] (or if you are unlucky, the kbd:[escape] key). Oh, and to get out of Emacs, do `C-x C-c` (that means hold down the kbd:[control] key, press kbd:[x], press kbd:[c] and release the kbd:[control] key). If you have any unsaved files open, Emacs will ask you if you want to save them. (Ignore the bit in the documentation where it says `C-z` is the usual way to leave Emacs-that leaves Emacs hanging around in the background, and is only really useful if you are on a system which does not have virtual terminals). === Configuring Emacs Emacs does many wonderful things; some of them are built in, some of them need to be configured. Instead of using a proprietary macro language for configuration, Emacs uses a version of Lisp specially adapted for editors, known as Emacs Lisp. Working with Emacs Lisp can be quite helpful if you want to go on and learn something like Common Lisp. Emacs Lisp has many features of Common Lisp, although it is considerably smaller (and thus easier to master). The best way to learn Emacs Lisp is to download the link:ftp://ftp.gnu.org/old-gnu/emacs/elisp-manual-19-2.4.tar.gz[Emacs Tutorial] However, there is no need to actually know any Lisp to get started with configuring Emacs, as I have included a sample [.filename]#.emacs#, which should be enough to get you started. Just copy it into your home directory and restart Emacs if it is already running; it will read the commands from the file and (hopefully) give you a useful basic setup. === A Sample [.filename]#.emacs# Unfortunately, there is far too much here to explain it in detail; however there are one or two points worth mentioning. * Everything beginning with a `;` is a comment and is ignored by Emacs. * In the first line, the `-*- Emacs-Lisp -*-` is so that we can edit [.filename]#.emacs# itself within Emacs and get all the fancy features for editing Emacs Lisp. Emacs usually tries to guess this based on the filename, and may not get it right for [.filename]#.emacs#. * The kbd:[tab] key is bound to an indentation function in some modes, so when you press the tab key, it will indent the current line of code. If you want to put a tab character in whatever you are writing, hold the kbd:[control] key down while you are pressing the kbd:[tab] key. * This file supports syntax highlighting for C, C++, Perl, Lisp and Scheme, by guessing the language from the filename. * Emacs already has a pre-defined function called `next-error`. In a compilation output window, this allows you to move from one compilation error to the next by doing `M-n`; we define a complementary function, `previous-error`, that allows you to go to a previous error by doing `M-p`. The nicest feature of all is that `C-c C-c` will open up the source file in which the error occurred and jump to the appropriate line. * We enable Emacs's ability to act as a server, so that if you are doing something outside Emacs and you want to edit a file, you can just type in + [source,bash] .... % emacsclient filename .... + and then you can edit the file in your Emacs!footnote:[Many Emacs users set their EDITOR environment to emacsclient so this happens every time they need to edit a file.] .A Sample [.filename]#.emacs# ==== [.programlisting] .... ;; -*-Emacs-Lisp-*- ;; This file is designed to be re-evaled; use the variable first-time ;; to avoid any problems with this. (defvar first-time t "Flag signifying this is the first time that .emacs has been evaled") ;; Meta (global-set-key "\M- " 'set-mark-command) (global-set-key "\M-\C-h" 'backward-kill-word) (global-set-key "\M-\C-r" 'query-replace) (global-set-key "\M-r" 'replace-string) (global-set-key "\M-g" 'goto-line) (global-set-key "\M-h" 'help-command) ;; Function keys (global-set-key [f1] 'manual-entry) (global-set-key [f2] 'info) (global-set-key [f3] 'repeat-complex-command) (global-set-key [f4] 'advertised-undo) (global-set-key [f5] 'eval-current-buffer) (global-set-key [f6] 'buffer-menu) (global-set-key [f7] 'other-window) (global-set-key [f8] 'find-file) (global-set-key [f9] 'save-buffer) (global-set-key [f10] 'next-error) (global-set-key [f11] 'compile) (global-set-key [f12] 'grep) (global-set-key [C-f1] 'compile) (global-set-key [C-f2] 'grep) (global-set-key [C-f3] 'next-error) (global-set-key [C-f4] 'previous-error) (global-set-key [C-f5] 'display-faces) (global-set-key [C-f8] 'dired) (global-set-key [C-f10] 'kill-compilation) ;; Keypad bindings (global-set-key [up] "\C-p") (global-set-key [down] "\C-n") (global-set-key [left] "\C-b") (global-set-key [right] "\C-f") (global-set-key [home] "\C-a") (global-set-key [end] "\C-e") (global-set-key [prior] "\M-v") (global-set-key [next] "\C-v") (global-set-key [C-up] "\M-\C-b") (global-set-key [C-down] "\M-\C-f") (global-set-key [C-left] "\M-b") (global-set-key [C-right] "\M-f") (global-set-key [C-home] "\M-<") (global-set-key [C-end] "\M->") (global-set-key [C-prior] "\M-<") (global-set-key [C-next] "\M->") ;; Mouse (global-set-key [mouse-3] 'imenu) ;; Misc (global-set-key [C-tab] "\C-q\t") ; Control tab quotes a tab. (setq backup-by-copying-when-mismatch t) ;; Treat 'y' or as yes, 'n' as no. (fset 'yes-or-no-p 'y-or-n-p) (define-key query-replace-map [return] 'act) (define-key query-replace-map [?\C-m] 'act) ;; Load packages (require 'desktop) (require 'tar-mode) ;; Pretty diff mode (autoload 'ediff-buffers "ediff" "Intelligent Emacs interface to diff" t) (autoload 'ediff-files "ediff" "Intelligent Emacs interface to diff" t) (autoload 'ediff-files-remote "ediff" "Intelligent Emacs interface to diff") (if first-time (setq auto-mode-alist (append '(("\\.cpp$" . c++-mode) ("\\.hpp$" . c++-mode) ("\\.lsp$" . lisp-mode) ("\\.scm$" . scheme-mode) ("\\.pl$" . perl-mode) ) auto-mode-alist))) ;; Auto font lock mode (defvar font-lock-auto-mode-list (list 'c-mode 'c++-mode 'c++-c-mode 'emacs-lisp-mode 'lisp-mode 'perl-mode 'scheme-mode) "List of modes to always start in font-lock-mode") (defvar font-lock-mode-keyword-alist '((c++-c-mode . c-font-lock-keywords) (perl-mode . perl-font-lock-keywords)) "Associations between modes and keywords") (defun font-lock-auto-mode-select () "Automatically select font-lock-mode if the current major mode is in font-lock-auto-mode-list" (if (memq major-mode font-lock-auto-mode-list) (progn (font-lock-mode t)) ) ) (global-set-key [M-f1] 'font-lock-fontify-buffer) ;; New dabbrev stuff ;(require 'new-dabbrev) (setq dabbrev-always-check-other-buffers t) (setq dabbrev-abbrev-char-regexp "\\sw\\|\\s_") (add-hook 'emacs-lisp-mode-hook '(lambda () (set (make-local-variable 'dabbrev-case-fold-search) nil) (set (make-local-variable 'dabbrev-case-replace) nil))) (add-hook 'c-mode-hook '(lambda () (set (make-local-variable 'dabbrev-case-fold-search) nil) (set (make-local-variable 'dabbrev-case-replace) nil))) (add-hook 'text-mode-hook '(lambda () (set (make-local-variable 'dabbrev-case-fold-search) t) (set (make-local-variable 'dabbrev-case-replace) t))) ;; C++ and C mode... (defun my-c++-mode-hook () (setq tab-width 4) (define-key c++-mode-map "\C-m" 'reindent-then-newline-and-indent) (define-key c++-mode-map "\C-ce" 'c-comment-edit) (setq c++-auto-hungry-initial-state 'none) (setq c++-delete-function 'backward-delete-char) (setq c++-tab-always-indent t) (setq c-indent-level 4) (setq c-continued-statement-offset 4) (setq c++-empty-arglist-indent 4)) (defun my-c-mode-hook () (setq tab-width 4) (define-key c-mode-map "\C-m" 'reindent-then-newline-and-indent) (define-key c-mode-map "\C-ce" 'c-comment-edit) (setq c-auto-hungry-initial-state 'none) (setq c-delete-function 'backward-delete-char) (setq c-tab-always-indent t) ;; BSD-ish indentation style (setq c-indent-level 4) (setq c-continued-statement-offset 4) (setq c-brace-offset -4) (setq c-argdecl-indent 0) (setq c-label-offset -4)) ;; Perl mode (defun my-perl-mode-hook () (setq tab-width 4) (define-key c++-mode-map "\C-m" 'reindent-then-newline-and-indent) (setq perl-indent-level 4) (setq perl-continued-statement-offset 4)) ;; Scheme mode... (defun my-scheme-mode-hook () (define-key scheme-mode-map "\C-m" 'reindent-then-newline-and-indent)) ;; Emacs-Lisp mode... (defun my-lisp-mode-hook () (define-key lisp-mode-map "\C-m" 'reindent-then-newline-and-indent) (define-key lisp-mode-map "\C-i" 'lisp-indent-line) (define-key lisp-mode-map "\C-j" 'eval-print-last-sexp)) ;; Add all of the hooks... (add-hook 'c++-mode-hook 'my-c++-mode-hook) (add-hook 'c-mode-hook 'my-c-mode-hook) (add-hook 'scheme-mode-hook 'my-scheme-mode-hook) (add-hook 'emacs-lisp-mode-hook 'my-lisp-mode-hook) (add-hook 'lisp-mode-hook 'my-lisp-mode-hook) (add-hook 'perl-mode-hook 'my-perl-mode-hook) ;; Complement to next-error (defun previous-error (n) "Visit previous compilation error message and corresponding source code." (interactive "p") (next-error (- n))) ;; Misc... (transient-mark-mode 1) (setq mark-even-if-inactive t) (setq visible-bell nil) (setq next-line-add-newlines nil) (setq compile-command "make") (setq suggest-key-bindings nil) (put 'eval-expression 'disabled nil) (put 'narrow-to-region 'disabled nil) (put 'set-goal-column 'disabled nil) (if (>= emacs-major-version 21) (setq show-trailing-whitespace t)) ;; Elisp archive searching (autoload 'format-lisp-code-directory "lispdir" nil t) (autoload 'lisp-dir-apropos "lispdir" nil t) (autoload 'lisp-dir-retrieve "lispdir" nil t) (autoload 'lisp-dir-verify "lispdir" nil t) ;; Font lock mode (defun my-make-face (face color &optional bold) "Create a face from a color and optionally make it bold" (make-face face) (copy-face 'default face) (set-face-foreground face color) (if bold (make-face-bold face)) ) (if (eq window-system 'x) (progn (my-make-face 'blue "blue") (my-make-face 'red "red") (my-make-face 'green "dark green") (setq font-lock-comment-face 'blue) (setq font-lock-string-face 'bold) (setq font-lock-type-face 'bold) (setq font-lock-keyword-face 'bold) (setq font-lock-function-name-face 'red) (setq font-lock-doc-string-face 'green) (add-hook 'find-file-hooks 'font-lock-auto-mode-select) (setq baud-rate 1000000) (global-set-key "\C-cmm" 'menu-bar-mode) (global-set-key "\C-cms" 'scroll-bar-mode) (global-set-key [backspace] 'backward-delete-char) ; (global-set-key [delete] 'delete-char) (standard-display-european t) (load-library "iso-transl"))) ;; X11 or PC using direct screen writes (if window-system (progn ;; (global-set-key [M-f1] 'hilit-repaint-command) ;; (global-set-key [M-f2] [?\C-u M-f1]) (setq hilit-mode-enable-list '(not text-mode c-mode c++-mode emacs-lisp-mode lisp-mode scheme-mode) hilit-auto-highlight nil hilit-auto-rehighlight 'visible hilit-inhibit-hooks nil hilit-inhibit-rebinding t) (require 'hilit19) (require 'paren)) (setq baud-rate 2400) ; For slow serial connections ) ;; TTY type terminal (if (and (not window-system) (not (equal system-type 'ms-dos))) (progn (if first-time (progn (keyboard-translate ?\C-h ?\C-?) (keyboard-translate ?\C-? ?\C-h))))) ;; Under UNIX (if (not (equal system-type 'ms-dos)) (progn (if first-time (server-start)))) ;; Add any face changes here (add-hook 'term-setup-hook 'my-term-setup-hook) (defun my-term-setup-hook () (if (eq window-system 'pc) (progn ;; (set-face-background 'default "red") ))) ;; Restore the "desktop" - do this as late as possible (if first-time (progn (desktop-load-default) (desktop-read))) ;; Indicate that this file has been read at least once (setq first-time nil) ;; No need to debug anything now (setq debug-on-error nil) ;; All done (message "All done, %s%s" (user-login-name) ".") .... ==== === Extending the Range of Languages Emacs Understands Now, this is all very well if you only want to program in the languages already catered for in [.filename]#.emacs# (C, C++, Perl, Lisp and Scheme), but what happens if a new language called "whizbang" comes out, full of exciting features? The first thing to do is find out if whizbang comes with any files that tell Emacs about the language. These usually end in [.filename]#.el#, short for "Emacs Lisp". For example, if whizbang is a FreeBSD port, we can locate these files by doing [source,bash] .... % find /usr/ports/lang/whizbang -name "*.el" -print .... -and install them by copying them into the Emacs site Lisp directory. On FreeBSD, this is [.filename]#/usr/local/shared/emacs/site-lisp#. +and install them by copying them into the Emacs site Lisp directory. On FreeBSD, this is [.filename]#/usr/local/share/emacs/site-lisp#. So for example, if the output from the find command was [source,bash] .... /usr/ports/lang/whizbang/work/misc/whizbang.el .... we would do [source,bash] .... -# cp /usr/ports/lang/whizbang/work/misc/whizbang.el /usr/local/shared/emacs/site-lisp +# cp /usr/ports/lang/whizbang/work/misc/whizbang.el /usr/local/share/emacs/site-lisp .... Next, we need to decide what extension whizbang source files have. Let us say for the sake of argument that they all end in [.filename]#.wiz#. We need to add an entry to our [.filename]#.emacs# to make sure Emacs will be able to use the information in [.filename]#whizbang.el#. Find the auto-mode-alist entry in [.filename]#.emacs# and add a line for whizbang, such as: [.programlisting] .... ... ("\\.lsp$" . lisp-mode) ("\\.wiz$" . whizbang-mode) ("\\.scm$" . scheme-mode) ... .... This means that Emacs will automatically go into `whizbang-mode` when you edit a file ending in [.filename]#.wiz#. Just below this, you will find the font-lock-auto-mode-list entry. Add `whizbang-mode` to it like so: [.programlisting] .... ;; Auto font lock mode (defvar font-lock-auto-mode-list (list 'c-mode 'c++-mode 'c++-c-mode 'emacs-lisp-mode 'whizbang-mode 'lisp-mode 'perl-mode 'scheme-mode) "List of modes to always start in font-lock-mode") .... This means that Emacs will always enable `font-lock-mode` (ie syntax highlighting) when editing a [.filename]#.wiz# file. And that is all that is needed. If there is anything else you want done automatically when you open up [.filename]#.wiz#, you can add a `whizbang-mode hook` (see `my-scheme-mode-hook` for a simple example that adds `auto-indent`). [[tools-reading]] == Further Reading For information about setting up a development environment for contributing fixes to FreeBSD itself, please see man:development[7]. * Brian Harvey and Matthew Wright _Simply Scheme_ MIT 1994. ISBN 0-262-08226-8 * Randall Schwartz _Learning Perl_ O'Reilly 1993 ISBN 1-56592-042-2 * Patrick Henry Winston and Berthold Klaus Paul Horn _Lisp (3rd Edition)_ Addison-Wesley 1989 ISBN 0-201-08319-1 * Brian W. Kernighan and Rob Pike _The Unix Programming Environment_ Prentice-Hall 1984 ISBN 0-13-937681-X * Brian W. Kernighan and Dennis M. Ritchie _The C Programming Language (2nd Edition)_ Prentice-Hall 1988 ISBN 0-13-110362-8 * Bjarne Stroustrup _The C++ Programming Language_ Addison-Wesley 1991 ISBN 0-201-53992-6 * W. Richard Stevens _Advanced Programming in the Unix Environment_ Addison-Wesley 1992 ISBN 0-201-56317-7 * W. Richard Stevens _Unix Network Programming_ Prentice-Hall 1990 ISBN 0-13-949876-1 diff --git a/documentation/content/en/books/fdp-primer/editor-config/_index.adoc b/documentation/content/en/books/fdp-primer/editor-config/_index.adoc index 429e00c04e..59ecbedc51 100644 --- a/documentation/content/en/books/fdp-primer/editor-config/_index.adoc +++ b/documentation/content/en/books/fdp-primer/editor-config/_index.adoc @@ -1,223 +1,223 @@ --- title: Chapter 12. Editor Configuration prev: books/fdp-primer/writing-style next: books/fdp-primer/see-also description: Configuration used in the texts editors in the FreeBSD Documentation Project tags: ["editor", "configuration", "vim", "emacs", "FreeBSD"] --- [[editor-config]] = Editor Configuration :doctype: book :toc: macro :toclevels: 1 :icons: font :sectnums: :sectnumlevels: 6 :source-highlighter: rouge :experimental: :skip-front-matter: :xrefstyle: basic :relfileprefix: ../ :outfilesuffix: :sectnumoffset: 12 toc::[] Adjusting your text editor configuration can make working on document files quicker and easier, and help documents conform to FDP guidelines. [[editor-config-vim]] == Vim Install from package:editors/vim[], package:editors/vim-console[], or package:editors/vim-tiny[] then follow the configuration instructions in <>. [[editor-config-vim-use]] === Use Press kbd:[P] to reformat paragraphs or text that has been selected in Visual mode. Press kbd:[T] to replace groups of eight spaces with a tab. [[editor-config-vim-config]] === Configuration Edit [.filename]#~/.vimrc#, adding these lines to the end of the file: [.programlisting] .... if has("autocmd") au BufNewFile,BufRead *.sgml,*.ent,*.xsl,*.xml call Set_SGML() au BufNewFile,BufRead *.[1-9] call ShowSpecial() endif " has(autocmd) function Set_Highlights() "match ExtraWhitespace /^\s* \s*\|\s\+$/ highlight default link OverLength ErrorMsg match OverLength /\%71v.\+/ return 0 endfunction " Set_Highlights() function ShowSpecial() setlocal list listchars=tab:>>,trail:*,eol:$ hi def link nontext ErrorMsg return 0 endfunction " ShowSpecial() function Set_SGML() setlocal number syn match sgmlSpecial "&[^;]*;" setlocal syntax=sgml setlocal filetype=xml setlocal shiftwidth=2 setlocal textwidth=70 setlocal tabstop=8 setlocal softtabstop=2 setlocal formatprg="fmt -p" setlocal autoindent setlocal smartindent " Rewrap paragraphs noremap P gqj " Replace spaces with tabs noremap T :s/ /\t/ call ShowSpecial() call Set_Highlights() return 0 endfunction " Set_SGML() .... [[editor-config-emacs]] == Emacs Install from package:editors/emacs[] or package:editors/emacs-devel[]. [[editor-config-emacs-validation]] === Validation Emacs's nxml-mode uses compact relax NG schemas for validating XML. A compact relax NG schema for FreeBSD's extension to DocBook 5.0 is included in the documentation repository. To configure nxml-mode to validate using this schema, create [.filename]#~/.emacs.d/schema/schemas.xml# and add these lines to the file: .... locatingRules xmlns="http://thaiopensource.com/ns/locating-rules/1.0" documentElement localName="section" typeId="DocBook" documentElement localName="chapter" typeId="DocBook" documentElement localName="article" typeId="DocBook" documentElement localName="book" typeId="DocBook" - typeId id="DocBook" uri="/usr/local/shared/xml/docbook/5.0/rng/docbook.rnc" + typeId id="DocBook" uri="/usr/local/share/xml/docbook/5.0/rng/docbook.rnc" locatingRules .... [[editor-config-emacs-igor]] === Automated Proofreading with Flycheck and Igor The Flycheck package is available from Milkypostman's Emacs Lisp Package Archive (MELPA). If MELPA is not already in Emacs's packages-archives, it can be added by evaluating .... (add-to-list 'package-archives '("melpa" . "http://stable.melpa.org/packages/") t) .... Add the line to Emacs's initialization file (one of [.filename]#~/.emacs#, [.filename]#~/.emacs.el#, or [.filename]#~.emacs.d/init.el#) to make this change permanent. To install Flycheck, evaluate .... (package-install 'flycheck) .... Create a Flycheck checker for package:textproc/igor[] by evaluating .... (flycheck-define-checker igor "FreeBSD Documentation Project sanity checker. See URLs https://www.freebsd.org/docproj/ and http://www.freshports.org/textproc/igor/." :command ("igor" "-X" source-inplace) :error-parser flycheck-parse-checkstyle :modes (nxml-mode) :standard-input t) (add-to-list 'flycheck-checkers 'igor 'append) .... Again, add these lines to Emacs's initialization file to make the changes permanent. [[editor-config-emacs-specifc]] === FreeBSD Documentation Specific Settings To apply settings specific to the FreeBSD documentation project, create [.filename]#.dir-locals.el# in the root directory of the documentation repository and add these lines to the file: .... ;;; Directory Local Variables ;;; For more information see (info "(emacs) Directory Variables") ((nxml-mode (eval . (turn-on-auto-fill)) (fill-column . 70) (eval . (require 'flycheck)) (eval . (flycheck-mode 1)) (flycheck-checker . igor) (eval . (add-to-list 'rng-schema-locating-files "~/.emacs.d/schema/schemas.xml")))) .... [[editor-config-nano]] == nano Install from package:editors/nano[] or package:editors/nano-devel[]. [[editor-config-nano-config]] === Configuration Copy the sample XML syntax highlight file to the user's home directory: [source,shell] .... -% cp /usr/local/shared/nano/xml.nanorc ~/.nanorc +% cp /usr/local/share/nano/xml.nanorc ~/.nanorc .... Use an editor to replace the lines in the [.filename]#~/.nanorc# `syntax "xml"` block with these rules: .... syntax "xml" "\.([jrs]html?|xml|xslt?)$" # trailing whitespace color ,blue "[[:space:]]+$" # multiples of eight spaces at the start a line # (after zero or more tabs) should be a tab color ,blue "^([TAB]*[ ]{8})+" # tabs after spaces color ,yellow "( )+TAB" # highlight indents that have an odd number of spaces color ,red "^(([ ]{2})+|(TAB+))*[ ]{1}[^ ]{1}" # lines longer than 70 characters color ,yellow "^(.{71})|(TAB.{63})|(TAB{2}.{55})|(TAB{3}.{47}).+$" .... Process the file to create embedded tabs: [source,shell] .... % perl -i'' -pe 's/TAB/\t/g' ~/.nanorc .... [[editor-config-nano-use]] === Use Specify additional helpful options when running the editor: [source,shell] .... % nano -AKipwz -r 70 -T8 _index.adoc .... Users of man:csh[1] can define an alias in [.filename]#~/.cshrc# to automate these options: .... alias nano "nano -AKipwz -r 70 -T8" .... After the alias is defined, the options will be added automatically: [source,shell] .... % nano _index.adoc .... diff --git a/documentation/content/en/books/handbook/introduction/_index.adoc b/documentation/content/en/books/handbook/introduction/_index.adoc index 3e5a7077d1..ea8d63aeda 100644 --- a/documentation/content/en/books/handbook/introduction/_index.adoc +++ b/documentation/content/en/books/handbook/introduction/_index.adoc @@ -1,225 +1,225 @@ --- title: Chapter 1. Introduction part: Part I. Getting Started prev: books/handbook/parti next: books/handbook/bsdinstall description: This chapter covers various aspects of the FreeBSD Project, such as its history, goals, development model, and so on tags: ["introduction", "synopsis", "about", "Who Uses FreeBSD", "goals", "history"] --- [[introduction]] = Introduction :doctype: book :toc: macro :toclevels: 1 :icons: font :sectnums: :sectnumlevels: 6 :source-highlighter: rouge :experimental: :skip-front-matter: :xrefstyle: basic :relfileprefix: ../ :outfilesuffix: :sectnumoffset: 1 ifeval::["{backend}" == "html5"] :imagesdir: ../../../../images/books/handbook/introduction/ endif::[] ifeval::["{backend}" == "pdf"] :imagesdir: ../../../../static/images/books/handbook/introduction/ endif::[] ifeval::["{backend}" == "epub3"] :imagesdir: ../../../../static/images/books/handbook/introduction/ endif::[] include::shared/authors.adoc[] include::shared/releases.adoc[] include::shared/en/mailing-lists.adoc[] include::shared/en/teams.adoc[] include::shared/en/urls.adoc[] toc::[] [[introduction-synopsis]] == Synopsis Thank you for your interest in FreeBSD! The following chapter covers various aspects of the FreeBSD Project, such as its history, goals, development model, and so on. After reading this chapter you will know: * How FreeBSD relates to other computer operating systems. * The history of the FreeBSD Project. * The goals of the FreeBSD Project. * The basics of the FreeBSD open-source development model. * And of course: where the name "FreeBSD" comes from. [[nutshell]] == Welcome to FreeBSD! FreeBSD is an Open Source, standards-compliant Unix-like operating system for x86 (both 32 and 64 bit), ARM(R), AArch64, RISC-V(R), MIPS(R), POWER(R), PowerPC(R), and Sun UltraSPARC(R) computers. It provides all the features that are nowadays taken for granted, such as preemptive multitasking, memory protection, virtual memory, multi-user facilities, SMP support, all the Open Source development tools for different languages and frameworks, and desktop features centered around X Window System, KDE, or GNOME. Its particular strengths are: * _Liberal Open Source license_, which grants you rights to freely modify and extend its source code and incorporate it in both Open Source projects and closed products without imposing restrictions typical to copyleft licenses, as well as avoiding potential license incompatibility problems. * _Strong TCP/IP networking_ - FreeBSD implements industry standard protocols with ever increasing performance and scalability. This makes it a good match in both server, and routing/firewalling roles - and indeed many companies and vendors use it precisely for that purpose. * _Fully integrated OpenZFS support_, including root-on-ZFS, ZFS Boot Environments, fault management, administrative delegation, support for jails, FreeBSD specific documentation, and system installer support. * _Extensive security features_, from the Mandatory Access Control framework to Capsicum capability and sandbox mechanisms. * _Over 30 thousand prebuilt packages_ for all supported architectures, and the Ports Collection which makes it easy to build your own, customized ones. * _Documentation_ - in addition to Handbook and books from different authors that cover topics ranging from system administration to kernel internals, there are also the man:man[1] pages, not only for userspace daemons, utilities, and configuration files, but also for kernel driver APIs (section 9) and individual drivers (section 4). * _Simple and consistent repository structure and build system_ - FreeBSD uses a single repository for all of its components, both kernel and userspace. This, along with an unified and easy to customize build system and a well thought out development process makes it easy to integrate FreeBSD with build infrastructure for your own product. * _Staying true to Unix philosophy_, preferring composability instead of monolithic "all in one" daemons with hardcoded behavior. * _Binary compatibility_ with Linux, which makes it possible to run many Linux binaries without the need for virtualisation. FreeBSD is based on the 4.4BSD-Lite release from Computer Systems Research Group (CSRG) at the University of California at Berkeley, and carries on the distinguished tradition of BSD systems development. In addition to the fine work provided by CSRG, the FreeBSD Project has put in many thousands of man-hours into extending the functionality and fine-tuning the system for maximum performance and reliability in real-life load situations. FreeBSD offers performance and reliability on par with other Open Source and commercial offerings, combined with cutting-edge features not available anywhere else. [[os-overview]] === What Can FreeBSD Do? The applications to which FreeBSD can be put are truly limited only by your own imagination. From software development to factory automation, inventory control to azimuth correction of remote satellite antennae; if it can be done with a commercial UNIX(R) product then it is more than likely that you can do it with FreeBSD too! FreeBSD also benefits significantly from literally thousands of high quality applications developed by research centers and universities around the world, often available at little to no cost. Because the source code for FreeBSD itself is freely available, the system can also be customized to an almost unheard of degree for special applications or projects, and in ways not generally possible with operating systems from most major commercial vendors. Here is just a sampling of some of the applications in which people are currently using FreeBSD: * _Internet Services:_ The robust TCP/IP networking built into FreeBSD makes it an ideal platform for a variety of Internet services such as: ** Web servers ** IPv4 and IPv6 routing ** Firewalls and NAT ("IP masquerading") gateways ** FTP servers ** Email servers ** And more... * _Education:_ Are you a student of computer science or a related engineering field? There is no better way of learning about operating systems, computer architecture and networking than the hands on, under the hood experience that FreeBSD can provide. A number of freely available CAD, mathematical and graphic design packages also make it highly useful to those whose primary interest in a computer is to get _other_ work done! * _Research:_ With source code for the entire system available, FreeBSD is an excellent platform for research in operating systems as well as other branches of computer science. FreeBSD's freely available nature also makes it possible for remote groups to collaborate on ideas or shared development without having to worry about special licensing agreements or limitations on what may be discussed in open forums. * _Networking:_ Need a new router? A name server (DNS)? A firewall to keep people out of your internal network? FreeBSD can easily turn that unused PC sitting in the corner into an advanced router with sophisticated packet-filtering capabilities. * _Embedded:_ FreeBSD makes an excellent platform to build embedded systems upon. With support for the ARM(R), MIPS(R) and PowerPC(R) platforms, coupled with a robust network stack, cutting edge features and the permissive link:{faq}#bsd-license-restrictions[BSD license] FreeBSD makes an excellent foundation for building embedded routers, firewalls, and other devices. * _Desktop:_ FreeBSD makes a fine choice for an inexpensive desktop solution using the freely available X11 server. FreeBSD offers a choice from many open-source desktop environments, including the standard GNOME and KDE graphical user interfaces. FreeBSD can even boot "diskless" from a central server, making individual workstations even cheaper and easier to administer. * _Software Development:_ The basic FreeBSD system comes with a full suite of development tools including a full C/C++ compiler and debugger suite. Support for many other languages are also available through the ports and packages collection. FreeBSD is available to download free of charge, or can be obtained on either CD-ROM or DVD. Please see crossref:mirrors[mirrors, Obtaining FreeBSD] for more information about obtaining FreeBSD. [[introduction-nutshell-users]] === Who Uses FreeBSD? FreeBSD has been known for its web serving capabilities - sites that run on FreeBSD include https://news.ycombinator.com/[Hacker News], http://www.netcraft.com/[Netcraft], http://www.163.com/[NetEase], https://signup.netflix.com/openconnect[Netflix], http://www.sina.com/[Sina], http://www.sony.co.jp/[Sony Japan], http://www.rambler.ru/[Rambler], http://www.yahoo.com/[Yahoo!], and http://www.yandex.ru/[Yandex]. FreeBSD's advanced features, proven security, predictable release cycle, and permissive license have led to its use as a platform for building many commercial and open source appliances, devices, and products. Many of the world's largest IT companies use FreeBSD: * http://www.apache.org/[Apache] - The Apache Software Foundation runs most of its public facing infrastructure, including possibly one of the largest SVN repositories in the world with over 1.4 million commits, on FreeBSD. * http://www.apple.com/[Apple] - OS X borrows heavily from FreeBSD for the network stack, virtual file system, and many userland components. Apple iOS also contains elements borrowed from FreeBSD. * http://www.cisco.com/[Cisco] - IronPort network security and anti-spam appliances run a modified FreeBSD kernel. * http://www.citrix.com/[Citrix] - The NetScaler line of security appliances provide layer 4-7 load balancing, content caching, application firewall, secure VPN, and mobile cloud network access, along with the power of a FreeBSD shell. * https://www.emc.com/isilon[Dell EMC Isilon] - Isilon's enterprise storage appliances are based on FreeBSD. The extremely liberal FreeBSD license allowed Isilon to integrate their intellectual property throughout the kernel and focus on building their product instead of an operating system. * http://www.quest.com/KACE[Quest KACE] - The KACE system management appliances run FreeBSD because of its reliability, scalability, and the community that supports its continued development. * http://www.ixsystems.com/[iXsystems] - The TrueNAS line of unified storage appliances is based on FreeBSD. In addition to their commercial products, iXsystems also manages development of the open source projects TrueOS and FreeNAS. * http://www.juniper.net/[Juniper] - The JunOS operating system that powers all Juniper networking gear (including routers, switches, security, and networking appliances) is based on FreeBSD. Juniper is one of many vendors that showcases the symbiotic relationship between the project and vendors of commercial products. Improvements generated at Juniper are upstreamed into FreeBSD to reduce the complexity of integrating new features from FreeBSD back into JunOS in the future. * http://www.mcafee.com/[McAfee] - SecurOS, the basis of McAfee enterprise firewall products including Sidewinder is based on FreeBSD. * http://www.netapp.com/[NetApp] - The Data ONTAP GX line of storage appliances are based on FreeBSD. In addition, NetApp has contributed back many features, including the new BSD licensed hypervisor, bhyve. * http://www.netflix.com/[Netflix] - The OpenConnect appliance that Netflix uses to stream movies to its customers is based on FreeBSD. Netflix has made extensive contributions to the codebase and works to maintain a zero delta from mainline FreeBSD. Netflix OpenConnect appliances are responsible for delivering more than 32% of all Internet traffic in North America. * http://www.sandvine.com/[Sandvine] - Sandvine uses FreeBSD as the basis of their high performance real-time network processing platforms that make up their intelligent network policy control products. * http://www.sony.com/[Sony] - The PlayStation 4 gaming console runs a modified version of FreeBSD. * http://www.sophos.com/[Sophos] - The Sophos Email Appliance product is based on a hardened FreeBSD and scans inbound mail for spam and viruses, while also monitoring outbound mail for malware as well as the accidental loss of sensitive information. * http://www.spectralogic.com/[Spectra Logic] - The nTier line of archive grade storage appliances run FreeBSD and OpenZFS. * https://www.stormshield.com[Stormshield] - Stormshield Network Security appliances are based on a hardened version of FreeBSD. The BSD license allows them to integrate their own intellectual property with the system while returning a great deal of interesting development to the community. * http://www.weather.com/[The Weather Channel] - The IntelliStar appliance that is installed at each local cable provider's headend and is responsible for injecting local weather forecasts into the cable TV network's programming runs FreeBSD. * http://www.verisign.com/[Verisign] - Verisign is responsible for operating the .com and .net root domain registries as well as the accompanying DNS infrastructure. They rely on a number of different network operating systems including FreeBSD to ensure there is no common point of failure in their infrastructure. * http://www.voxer.com/[Voxer] - Voxer powers their mobile voice messaging platform with ZFS on FreeBSD. Voxer switched from a Solaris derivative to FreeBSD because of its superior documentation, larger and more active community, and more developer friendly environment. In addition to critical features like ZFS and DTrace, FreeBSD also offers TRIM support for ZFS. * https://fudosecurity.com/en/[Fudo Security] - The FUDO security appliance allows enterprises to monitor, control, record, and audit contractors and administrators who work on their systems. Based on all of the best security features of FreeBSD including ZFS, GELI, Capsicum, HAST, and auditdistd. FreeBSD has also spawned a number of related open source projects: * http://bsdrp.net/[BSD Router] - A FreeBSD based replacement for large enterprise routers designed to run on standard PC hardware. * http://www.freenas.org/[FreeNAS] - A customized FreeBSD designed to be used as a network file server appliance. Provides a python based web interface to simplify the management of both the UFS and ZFS file systems. Includes support for NFS, SMB/CIFS, AFP, FTP, and iSCSI. Includes an extensible plugin system based on FreeBSD jails. * https://ghostbsd.org/[GhostBSD] - is derived from FreeBSD, uses the GTK environment to provide a beautiful looks and comfortable experience on the modern BSD platform offering a natural and native UNIX(R) work environment. * http://mfsbsd.vx.sk/[mfsBSD] - A toolkit for building a FreeBSD system image that runs entirely from memory. * http://www.nas4free.org/[NAS4Free] - A file server distribution based on FreeBSD with a PHP powered web interface. * http://www.opnsense.org/[OPNSense] - OPNsense is an open source, easy-to-use and easy-to-build FreeBSD based firewall and routing platform. OPNsense includes most of the features available in expensive commercial firewalls, and more in many cases. It brings the rich feature set of commercial offerings with the benefits of open and verifiable sources. * https://www.trueos.org[TrueOS] - TrueOS is based on the legendary security and stability of FreeBSD. TrueOS follows FreeBSD-CURRENT, with the latest drivers, security updates, and packages available. * https://www.midnightbsd.org[MidnightBSD] - is a FreeBSD derived operating system developed with desktop users in mind. It includes all the software you'd expect for your daily tasks: mail, web browsing, word processing, gaming, and much more. * https://www.nomadbsd.org[NomadBSD] - is a persistent live system for USB flash drives, based on FreeBSD. Together with automatic hardware detection and setup, it is configured to be used as a desktop system that works out of the box, but can also be used for data recovery, for educational purposes, or to test FreeBSD's hardware compatibility. * http://www.pfsense.org/[pfSense] - A firewall distribution based on FreeBSD with a huge array of features and extensive IPv6 support. * http://zrouter.org/[ZRouter] - An open source alternative firmware for embedded devices based on FreeBSD. Designed to replace the proprietary firmware on off-the-shelf routers. A list of https://www.freebsdfoundation.org/about/testimonials/[testimonials from companies basing their products and services on FreeBSD] can be found at the FreeBSD Foundation website. Wikipedia also maintains a https://en.wikipedia.org/wiki/List_of_products_based_on_FreeBSD[list of products based on FreeBSD]. [[history]] == About the FreeBSD Project The following section provides some background information on the project, including a brief history, project goals, and the development model of the project. [[intro-history]] === A Brief History of FreeBSD The FreeBSD Project had its genesis in the early part of 1993, partially as the brainchild of the Unofficial 386BSDPatchkit's last 3 coordinators: Nate Williams, Rod Grimes and Jordan Hubbard. The original goal was to produce an intermediate snapshot of 386BSD in order to fix a number of problems that the patchkit mechanism was just not capable of solving. The early working title for the project was 386BSD 0.5 or 386BSD Interim in reference of that fact. 386BSD was Bill Jolitz's operating system, which had been up to that point suffering rather severely from almost a year's worth of neglect. As the patchkit swelled ever more uncomfortably with each passing day, they decided to assist Bill by providing this interim "cleanup" snapshot. Those plans came to a rude halt when Bill Jolitz suddenly decided to withdraw his sanction from the project without any clear indication of what would be done instead. The trio thought that the goal remained worthwhile, even without Bill's support, and so they adopted the name "FreeBSD" coined by David Greenman. The initial objectives were set after consulting with the system's current users and, once it became clear that the project was on the road to perhaps even becoming a reality, Jordan contacted Walnut Creek CDROM with an eye toward improving FreeBSD's distribution channels for those many unfortunates without easy access to the Internet. Walnut Creek CDROM not only supported the idea of distributing FreeBSD on CD but also went so far as to provide the project with a machine to work on and a fast Internet connection. Without Walnut Creek CDROM's almost unprecedented degree of faith in what was, at the time, a completely unknown project, it is quite unlikely that FreeBSD would have gotten as far, as fast, as it has today. The first CD-ROM (and general net-wide) distribution was FreeBSD 1.0, released in December of 1993. This was based on the 4.3BSD-Lite ("Net/2") tape from U.C. Berkeley, with many components also provided by 386BSD and the Free Software Foundation. It was a fairly reasonable success for a first offering, and they followed it with the highly successful FreeBSD 1.1 release in May of 1994. Around this time, some rather unexpected storm clouds formed on the horizon as Novell and U.C. Berkeley settled their long-running lawsuit over the legal status of the Berkeley Net/2 tape. A condition of that settlement was U.C. Berkeley's concession that large parts of Net/2 were "encumbered" code and the property of Novell, who had in turn acquired it from AT&T some time previously. What Berkeley got in return was Novell's "blessing" that the 4.4BSD-Lite release, when it was finally released, would be declared unencumbered and all existing Net/2 users would be strongly encouraged to switch. This included FreeBSD, and the project was given until the end of July 1994 to stop shipping its own Net/2 based product. Under the terms of that agreement, the project was allowed one last release before the deadline, that release being FreeBSD 1.1.5.1. FreeBSD then set about the arduous task of literally re-inventing itself from a completely new and rather incomplete set of 4.4BSD-Lite bits. The "Lite" releases were light in part because Berkeley's CSRG had removed large chunks of code required for actually constructing a bootable running system (due to various legal requirements) and the fact that the Intel port of 4.4 was highly incomplete. It took the project until November of 1994 to make this transition, and in December it released FreeBSD 2.0 to the world. Despite being still more than a little rough around the edges, the release was a significant success and was followed by the more robust and easier to install FreeBSD 2.0.5 release in June of 1995. Since that time, FreeBSD has made a series of releases each time improving the stability, speed, and feature set of the previous version. For now, long-term development projects continue to take place in the 10.X-CURRENT (trunk) branch, and snapshot releases of 10.X are continually made available from link:ftp://ftp.FreeBSD.org/pub/FreeBSD/snapshots/[the snapshot server] as work progresses. [[goals]] === FreeBSD Project Goals The goals of the FreeBSD Project are to provide software that may be used for any purpose and without strings attached. Many of us have a significant investment in the code (and project) and would certainly not mind a little financial compensation now and then, but we are definitely not prepared to insist on it. We believe that our first and foremost "mission" is to provide code to any and all comers, and for whatever purpose, so that the code gets the widest possible use and provides the widest possible benefit. This is, I believe, one of the most fundamental goals of Free Software and one that we enthusiastically support. That code in our source tree which falls under the GNU General Public License (GPL) or Library General Public License (LGPL) comes with slightly more strings attached, though at least on the side of enforced access rather than the usual opposite. Due to the additional complexities that can evolve in the commercial use of GPL software we do, however, prefer software submitted under the more relaxed BSD license when it is a reasonable option to do so. [[development]] === The FreeBSD Development Model The development of FreeBSD is a very open and flexible process, being literally built from the contributions of thousands of people around the world, as can be seen from our link:{contributors}[list of contributors]. FreeBSD's development infrastructure allow these thousands of contributors to collaborate over the Internet. We are constantly on the lookout for new developers and ideas, and those interested in becoming more closely involved with the project need simply contact us at the {freebsd-hackers}. The {freebsd-announce} is also available to those wishing to make other FreeBSD users aware of major areas of work. Useful things to know about the FreeBSD Project and its development process, whether working independently or in close cooperation: The SVN repositories[[development-cvs-repository]]:: For several years, the central source tree for FreeBSD was maintained by http://www.nongnu.org/cvs/[CVS] (Concurrent Versions System), a freely available source code control tool. In June 2008, the Project switched to using http://subversion.tigris.org[SVN] (Subversion). The switch was deemed necessary, as the technical limitations imposed by CVS were becoming obvious due to the rapid expansion of the source tree and the amount of history already stored. The Documentation Project and Ports Collection repositories also moved from CVS to SVN in May 2012 and July 2012, respectively. Please refer to the crossref:cutting-edge[synching, Obtaining the Source] section for more information on obtaining the FreeBSD `src/` repository and crossref:ports[ports-using, Using the Ports Collection] for details on obtaining the FreeBSD Ports Collection. The committers list[[development-committers]]:: The _committers_ are the people who have _write_ access to the Subversion tree, and are authorized to make modifications to the FreeBSD source (the term "committer" comes from `commit`, the source control command which is used to bring new changes into the repository). Anyone can submit a bug to the https://bugs.FreeBSD.org/submit/[Bug Database]. Before submitting a bug report, the FreeBSD mailing lists, IRC channels, or forums can be used to help verify that an issue is actually a bug. The FreeBSD core team[[development-core]]:: The _FreeBSD core team_ would be equivalent to the board of directors if the FreeBSD Project were a company. The primary task of the core team is to make sure the project, as a whole, is in good shape and is heading in the right directions. Inviting dedicated and responsible developers to join our group of committers is one of the functions of the core team, as is the recruitment of new core team members as others move on. The current core team was elected from a pool of committer candidates in June 2020. Elections are held every 2 years. + [NOTE] ==== Like most developers, most members of the core team are also volunteers when it comes to FreeBSD development and do not benefit from the project financially, so "commitment" should also not be misconstrued as meaning "guaranteed support." The "board of directors" analogy above is not very accurate, and it may be more suitable to say that these are the people who gave up their lives in favor of FreeBSD against their better judgement! ==== Outside contributors:: Last, but definitely not least, the largest group of developers are the users themselves who provide feedback and bug fixes to us on an almost constant basis. The primary way of keeping in touch with FreeBSD's more non-centralized development is to subscribe to the {freebsd-hackers} where such things are discussed. See crossref:eresources[eresources, Resources on the Internet] for more information about the various FreeBSD mailing lists. + link:{contributors}[The FreeBSD Contributors List] is a long and growing one, so why not join it by contributing something back to FreeBSD today? + Providing code is not the only way of contributing to the project; for a more complete list of things that need doing, please refer to the link:https://www.FreeBSD.org/[FreeBSD Project web site]. In summary, our development model is organized as a loose set of concentric circles. The centralized model is designed for the convenience of the _users_ of FreeBSD, who are provided with an easy way of tracking one central code base, not to keep potential contributors out! Our desire is to present a stable operating system with a large set of coherent crossref:ports[ports,application programs] that the users can easily install and use - this model works very well in accomplishing that. All we ask of those who would join us as FreeBSD developers is some of the same dedication its current people have to its continued success! [[third-party-programs]] === Third Party Programs In addition to the base distributions, FreeBSD offers a ported software collection with thousands of commonly sought-after programs. At the time of this writing, there were over {numports} ports! The list of ports ranges from http servers, to games, languages, editors, and almost everything in between. The entire Ports Collection requires approximately {ports-size}. To compile a port, you simply change to the directory of the program you wish to install, type `make install`, and let the system do the rest. The full original distribution for each port you build is retrieved dynamically so you need only enough disk space to build the ports you want. Almost every port is also provided as a pre-compiled "package", which can be installed with a simple command (`pkg install`) by those who do not wish to compile their own ports from source. More information on packages and ports can be found in crossref:ports[ports,Installing Applications: Packages and Ports]. === Additional Documentation -All supported FreeBSD versions provide an option in the installer to install additional documentation under [.filename]#/usr/local/shared/doc/freebsd# during the initial system setup. Documentation may also be installed at any later time using packages as described in crossref:cutting-edge[doc-ports-install-package,“Updating Documentation from Ports”]. You may view the locally installed manuals with any HTML capable browser using the following URLs: +All supported FreeBSD versions provide an option in the installer to install additional documentation under [.filename]#/usr/local/share/doc/freebsd# during the initial system setup. Documentation may also be installed at any later time using packages as described in crossref:cutting-edge[doc-ports-install-package,Updating Documentation from Ports]. You may view the locally installed manuals with any HTML capable browser using the following URLs: The FreeBSD Handbook:: -[.filename]#link:file://localhost/usr/local/shared/doc/freebsd/handbook/index.html[/usr/local/shared/doc/freebsd/handbook/index.html]# +[.filename]#link:file://localhost/usr/local/share/doc/freebsd/handbook/index.html[/usr/local/share/doc/freebsd/handbook/index.html]# The FreeBSD FAQ:: -[.filename]#link:file://localhost/usr/local/shared/doc/freebsd/faq/index.html[/usr/local/shared/doc/freebsd/faq/index.html]# +[.filename]#link:file://localhost/usr/local/share/doc/freebsd/faq/index.html[/usr/local/share/doc/freebsd/faq/index.html]# You can also view the master (and most frequently updated) copies at https://www.FreeBSD.org/[https://www.FreeBSD.org/]. diff --git a/documentation/content/en/books/handbook/l10n/_index.adoc b/documentation/content/en/books/handbook/l10n/_index.adoc index 51d4f4f363..b7f0814f97 100644 --- a/documentation/content/en/books/handbook/l10n/_index.adoc +++ b/documentation/content/en/books/handbook/l10n/_index.adoc @@ -1,585 +1,585 @@ --- title: Chapter 23. Localization - i18n/L10n Usage and Setup part: Part III. System Administration prev: books/handbook/virtualization next: books/handbook/cutting-edge description: FreeBSD supports localization into many languages, allowing users to view, input, or process data in non-English languages tags: ["i18n", "L10n", "localization", "Locale", "LANG", "MM_CHARSET", "cap_mkdb"] --- [[l10n]] = Localization - i18n/L10n Usage and Setup :doctype: book :toc: macro :toclevels: 1 :icons: font :sectnums: :sectnumlevels: 6 :source-highlighter: rouge :experimental: :skip-front-matter: :xrefstyle: basic :relfileprefix: ../ :outfilesuffix: :sectnumoffset: 23 ifeval::["{backend}" == "html5"] :imagesdir: ../../../../images/books/handbook/l10n/ endif::[] ifeval::["{backend}" == "pdf"] :imagesdir: ../../../../static/images/books/handbook/l10n/ endif::[] ifeval::["{backend}" == "epub3"] :imagesdir: ../../../../static/images/books/handbook/l10n/ endif::[] include::shared/authors.adoc[] include::shared/releases.adoc[] include::shared/en/mailing-lists.adoc[] include::shared/en/teams.adoc[] include::shared/en/urls.adoc[] toc::[] [[l10n-synopsis]] == Synopsis FreeBSD is a distributed project with users and contributors located all over the world. As such, FreeBSD supports localization into many languages, allowing users to view, input, or process data in non-English languages. One can choose from most of the major languages, including, but not limited to: Chinese, German, Japanese, Korean, French, Russian, and Vietnamese. The term internationalization has been shortened to i18n, which represents the number of letters between the first and the last letters of `internationalization`. L10n uses the same naming scheme, but from `localization`. The i18n/L10n methods, protocols, and applications allow users to use languages of their choice. This chapter discusses the internationalization and localization features of FreeBSD. After reading this chapter, you will know: * How locale names are constructed. * How to set the locale for a login shell. * How to configure the console for non-English languages. * How to configure Xorg for different languages. * How to find i18n-compliant applications. * Where to find more information for configuring specific languages. Before reading this chapter, you should: * Know how to crossref:ports[ports,install additional third-party applications]. [[using-localization]] == Using Localization Localization settings are based on three components: the language code, country code, and encoding. Locale names are constructed from these parts as follows: [.programlisting] .... LanguageCode_CountryCode.Encoding .... The _LanguageCode_ and _CountryCode_ are used to determine the country and the specific language variation. <> provides some examples of __LanguageCode_CountryCode__: [[locale-lang-country]] .Common Language and Country Codes [cols="1,1", frame="none", options="header"] |=== | LanguageCode_Country Code | Description |en_US |English, United States |ru_RU |Russian, Russia |zh_TW |Traditional Chinese, Taiwan |=== A complete listing of available locales can be found by typing: [source,shell] .... % locale -a | more .... To determine the current locale setting: [source,shell] .... % locale .... Language specific character sets, such as ISO8859-1, ISO8859-15, KOI8-R, and CP437, are described in man:multibyte[3]. The active list of character sets can be found at the http://www.iana.org/assignments/character-sets[IANA Registry]. Some languages, such as Chinese or Japanese, cannot be represented using ASCII characters and require an extended language encoding using either wide or multibyte characters. Examples of wide or multibyte encodings include EUC and Big5. Older applications may mistake these encodings for control characters while newer applications usually recognize these characters. Depending on the implementation, users may be required to compile an application with wide or multibyte character support, or to configure it correctly. [NOTE] ==== FreeBSD uses Xorg-compatible locale encodings. ==== The rest of this section describes the various methods for configuring the locale on a FreeBSD system. The next section will discuss the considerations for finding and compiling applications with i18n support. [[setting-locale]] === Setting Locale for Login Shell Locale settings are configured either in a user's [.filename]#~/.login_conf# or in the startup file of the user's shell: [.filename]#~/.profile#, [.filename]#~/.bashrc#, or [.filename]#~/.cshrc#. Two environment variables should be set: * `LANG`, which sets the locale * `MM_CHARSET`, which sets the MIME character set used by applications In addition to the user's shell configuration, these variables should also be set for specific application configuration and Xorg configuration. Two methods are available for making the needed variable assignments: the <> method, which is the recommended method, and the <> method. The next two sections demonstrate how to use both methods. [[login-class]] ==== Login Classes Method This first method is the recommended method as it assigns the required environment variables for locale name and MIME character sets for every possible shell. This setup can either be performed by each user or it can be configured for all users by the superuser. This minimal example sets both variables for Latin-1 encoding in the [.filename]#.login_conf# of an individual user's home directory: [.programlisting] .... me:\ :charset=ISO-8859-1:\ :lang=de_DE.ISO8859-1: .... Here is an example of a user's [.filename]#~/.login_conf# that sets the variables for Traditional Chinese in BIG-5 encoding. More variables are needed because some applications do not correctly respect locale variables for Chinese, Japanese, and Korean: [.programlisting] .... #Users who do not wish to use monetary units or time formats #of Taiwan can manually change each variable me:\ :lang=zh_TW.Big5:\ :setenv=LC_ALL=zh_TW.Big5,LC_COLLATE=zh_TW.Big5,LC_CTYPE=zh_TW.Big5,LC_MESSAGES=zh_TW.Big5,LC_MONETARY=zh_TW.Big5,LC_NUMERIC=zh_TW.Big5,LC_TIME=zh_TW.Big5:\ :charset=big5:\ :xmodifiers="@im=gcin": #Set gcin as the XIM Input Server .... Alternately, the superuser can configure all users of the system for localization. The following variables in [.filename]#/etc/login.conf# are used to set the locale and MIME character set: [.programlisting] .... language_name|Account Type Description:\ :charset=MIME_charset:\ :lang=locale_name:\ :tc=default: .... So, the previous Latin-1 example would look like this: [.programlisting] .... german|German Users Accounts:\ :charset=ISO-8859-1:\ :lang=de_DE.ISO8859-1:\ :tc=default: .... See man:login.conf[5] for more details about these variables. Note that it already contains pre-defined _russian_ class. Whenever [.filename]#/etc/login.conf# is edited, remember to execute the following command to update the capability database: [source,shell] .... # cap_mkdb /etc/login.conf .... [NOTE] ==== For an end user, the `cap_mkdb` command will need to be run on their [.filename]#~/.login_conf# for any changes to take effect. ==== ===== Utilities Which Change Login Classes In addition to manually editing [.filename]#/etc/login.conf#, several utilities are available for setting the locale for newly created users. When using `vipw` to add new users, specify the _language_ to set the locale: [.programlisting] .... user:password:1111:11:language:0:0:User Name:/home/user:/bin/sh .... When using `adduser` to add new users, the default language can be pre-configured for all new users or specified for an individual user. If all new users use the same language, set `defaultclass=_language_` in [.filename]#/etc/adduser.conf#. To override this setting when creating a user, either input the required locale at this prompt: [source,shell] .... Enter login class: default []: .... or specify the locale to set when invoking `adduser`: [source,shell] .... # adduser -class language .... If `pw` is used to add new users, specify the locale as follows: [source,shell] .... # pw useradd user_name -L language .... To change the login class of an existing user, `chpass` can be used. Invoke it as superuser and provide the username to edit as the argument. [source,shell] .... # chpass user_name .... [[startup-file]] ==== Shell Startup File Method This second method is not recommended as each shell that is used requires manual configuration, where each shell has a different configuration file and differing syntax. As an example, to set the German language for the `sh` shell, these lines could be added to [.filename]#~/.profile# to set the shell for that user only. These lines could also be added to [.filename]#/etc/profile# or [.filename]#/usr/share/skel/dot.profile# to set that shell for all users: [.programlisting] .... LANG=de_DE.ISO8859-1; export LANG MM_CHARSET=ISO-8859-1; export MM_CHARSET .... However, the name of the configuration file and the syntax used differs for the `csh` shell. These are the equivalent settings for [.filename]#~/.login#, [.filename]#/etc/csh.login#, or [.filename]#/usr/share/skel/dot.login#: [.programlisting] .... setenv LANG de_DE.ISO8859-1 setenv MM_CHARSET ISO-8859-1 .... To complicate matters, the syntax needed to configure Xorg in [.filename]#~/.xinitrc# also depends upon the shell. The first example is for the `sh` shell and the second is for the `csh` shell: [.programlisting] .... LANG=de_DE.ISO8859-1; export LANG .... [.programlisting] .... setenv LANG de_DE.ISO8859-1 .... [[setting-console]] === Console Setup Several localized fonts are available for the console. To see a listing of available fonts, type `ls /usr/share/syscons/fonts`. To configure the console font, specify the _font_name_, without the [.filename]#.fnt# suffix, in [.filename]#/etc/rc.conf#: [.programlisting] .... font8x16=font_name font8x14=font_name font8x8=font_name .... The keymap and screenmap can be set by adding the following to [.filename]#/etc/rc.conf#: [.programlisting] .... scrnmap=screenmap_name keymap=keymap_name keychange="fkey_number sequence" .... To see the list of available screenmaps, type `ls /usr/share/syscons/scrnmaps`. Do not include the [.filename]#.scm# suffix when specifying _screenmap_name_. A screenmap with a corresponding mapped font is usually needed as a workaround for expanding bit 8 to bit 9 on a VGA adapter's font character matrix so that letters are moved out of the pseudographics area if the screen font uses a bit 8 column. To see the list of available keymaps, type `ls /usr/share/syscons/keymaps`. When specifying the _keymap_name_, do not include the [.filename]#.kbd# suffix. To test keymaps without rebooting, use man:kbdmap[1]. The `keychange` entry is usually needed to program function keys to match the selected terminal type because function key sequences cannot be defined in the keymap. Next, set the correct console terminal type in [.filename]#/etc/ttys# for all virtual terminal entries. <> summarizes the available terminal types.: [[locale-charset]] .Defined Terminal Types for Character Sets [cols="1,1", frame="none", options="header"] |=== | Character Set | Terminal Type |ISO8859-1 or ISO8859-15 |`cons25l1` |ISO8859-2 |`cons25l2` |ISO8859-7 |`cons25l7` |KOI8-R |`cons25r` |KOI8-U |`cons25u` |CP437 (VGA default) |`cons25` |US-ASCII |`cons25w` |=== For languages with wide or multibyte characters, install a console for that language from the FreeBSD Ports Collection. The available ports are summarized in <>. Once installed, refer to the port's [.filename]#pkg-message# or man pages for configuration and usage instructions. [[locale-console]] .Available Console from Ports Collection [cols="1,1", frame="none", options="header"] |=== | Language | Port Location |Traditional Chinese (BIG-5) |package:chinese/big5con[] |Chinese/Japanese/Korean |package:chinese/cce[] |Chinese/Japanese/Korean |package:chinese/zhcon[] |Japanese |package:chinese/kon2[] |Japanese |package:japanese/kon2-14dot[] |Japanese |package:japanese/kon2-16dot[] |=== If moused is enabled in [.filename]#/etc/rc.conf#, additional configuration may be required. By default, the mouse cursor of the man:syscons[4] driver occupies the `0xd0`-`0xd3` range in the character set. If the language uses this range, move the cursor's range by adding the following line to [.filename]#/etc/rc.conf#: [.programlisting] .... mousechar_start=3 .... === Xorg Setup crossref:x11[x11,The X Window System] describes how to install and configure Xorg. When configuring Xorg for localization, additional fonts and input methods are available from the FreeBSD Ports Collection. Application specific i18n settings such as fonts and menus can be tuned in [.filename]#~/.Xresources# and should allow users to view their selected language in graphical application menus. The X Input Method (XIM) protocol is an Xorg standard for inputting non-English characters. <> summarizes the input method applications which are available in the FreeBSD Ports Collection. Additional Fcitx and Uim applications are also available. [[locale-xim]] .Available Input Methods [cols="1,1", frame="none", options="header"] |=== | Language | Input Method |Chinese |package:chinese/gcin[] |Chinese |package:chinese/ibus-chewing[] |Chinese |package:chinese/ibus-pinyin[] |Chinese |package:chinese/oxim[] |Chinese |package:chinese/scim-fcitx[] |Chinese |package:chinese/scim-pinyin[] |Chinese |package:chinese/scim-tables[] |Japanese |package:japanese/ibus-anthy[] |Japanese |package:japanese/ibus-mozc[] |Japanese |package:japanese/ibus-skk[] |Japanese |package:japanese/im-ja[] |Japanese |package:japanese/kinput2[] |Japanese |package:japanese/scim-anthy[] |Japanese |package:japanese/scim-canna[] |Japanese |package:japanese/scim-honoka[] |Japanese |package:japanese/scim-honoka-plugin-romkan[] |Japanese |package:japanese/scim-honoka-plugin-wnn[] |Japanese |package:japanese/scim-prime[] |Japanese |package:japanese/scim-skk[] |Japanese |package:japanese/scim-tables[] |Japanese |package:japanese/scim-tomoe[] |Japanese |package:japanese/scim-uim[] |Japanese |package:japanese/skkinput[] |Japanese |package:japanese/skkinput3[] |Japanese |package:japanese/uim-anthy[] |Korean |package:korean/ibus-hangul[] |Korean |package:korean/imhangul[] |Korean |package:korean/nabi[] |Korean |package:korean/scim-hangul[] |Korean |package:korean/scim-tables[] |Vietnamese |package:vietnamese/xvnkb[] |Vietnamese |package:vietnamese/x-unikey[] |=== [[l10n-compiling]] == Finding i18n Applications i18n applications are programmed using i18n kits under libraries. These allow developers to write a simple file and translate displayed menus and texts to each language. The link:https://www.FreeBSD.org/ports/[FreeBSD Ports Collection] contains many applications with built-in support for wide or multibyte characters for several languages. Such applications include `i18n` in their names for easy identification. However, they do not always support the language needed. Some applications can be compiled with the specific charset. This is usually done in the port's [.filename]#Makefile# or by passing a value to configure. Refer to the i18n documentation in the respective FreeBSD port's source for more information on how to determine the needed configure value or the port's [.filename]#Makefile# to determine which compile options to use when building the port. [[lang-setup]] == Locale Configuration for Specific Languages This section provides configuration examples for localizing a FreeBSD system for the Russian language. It then provides some additional resources for localizing other languages. [[ru-localize]] === Russian Language (KOI8-R Encoding) This section shows the specific settings needed to localize a FreeBSD system for the Russian language. Refer to <> for a more complete description of each type of setting. To set this locale for the login shell, add the following lines to each user's [.filename]#~/.login_conf#: [.programlisting] .... me:My Account:\ :charset=KOI8-R:\ :lang=ru_RU.KOI8-R: .... To configure the console, add the following lines to [.filename]#/etc/rc.conf#: [.programlisting] .... keymap="ru.utf-8" scrnmap="utf-82cp866" font8x16="cp866b-8x16" font8x14="cp866-8x14" font8x8="cp866-8x8" mousechar_start=3 .... For each `ttyv` entry in [.filename]#/etc/ttys#, use `cons25r` as the terminal type. To configure printing, a special output filter is needed to convert from KOI8-R to CP866 since most printers with Russian characters come with hardware code page CP866. FreeBSD includes a default filter for this purpose, [.filename]#/usr/libexec/lpr/ru/koi2alt#. To use this filter, add this entry to [.filename]#/etc/printcap#: [.programlisting] .... lp|Russian local line printer:\ :sh:of=/usr/libexec/lpr/ru/koi2alt:\ :lp=/dev/lpt0:sd=/var/spool/output/lpd:lf=/var/log/lpd-errs: .... Refer to man:printcap[5] for a more detailed explanation. To configure support for Russian filenames in mounted MS-DOS(R) file systems, include `-L` and the locale name when adding an entry to [.filename]#/etc/fstab#: [.programlisting] .... /dev/ad0s2 /dos/c msdos rw,-Lru_RU.KOI8-R 0 0 .... Refer to man:mount_msdosfs[8] for more details. To configure Russian fonts for Xorg, install the package:x11-fonts/xorg-fonts-cyrillic[] package. Then, check the `"Files"` section in [.filename]#/etc/X11/xorg.conf#. The following line must be added _before_ any other `FontPath` entries: [.programlisting] .... FontPath "/usr/local/lib/X11/fonts/cyrillic" .... Additional Cyrillic fonts are available in the Ports Collection. To activate a Russian keyboard, add the following to the `"Keyboard"` section of [.filename]#/etc/xorg.conf#: [.programlisting] .... Option "XkbLayout" "us,ru" Option "XkbOptions" "grp:toggle" .... Make sure that `XkbDisable` is commented out in that file. For `grp:toggle` use kbd:[Right Alt], for `grp:ctrl_shift_toggle` use kbd[Ctrl+Shift]. For `grp:caps_toggle` use kbd:[CapsLock]. The old kbd:[CapsLock] function is still available in LAT mode only using kbd[Shift+CapsLock]. `grp:caps_toggle` does not work in Xorg for some unknown reason. If the keyboard has "Windows(R)" keys, and some non-alphabetical keys are mapped incorrectly, add the following line to [.filename]#/etc/xorg.conf#: [.programlisting] .... Option "XkbVariant" ",winkeys" .... [NOTE] ==== The Russian XKB keyboard may not work with non-localized applications. Minimally localized applications should call a `XtSetLanguageProc (NULL, NULL, NULL);` function early in the program. ==== See http://koi8.pp.ru/xwin.html[http://koi8.pp.ru/xwin.html] for more instructions on localizing Xorg applications. For more general information about KOI8-R encoding, refer to http://koi8.pp.ru/[http://koi8.pp.ru/]. === Additional Language-Specific Resources This section lists some additional resources for configuring other locales. Traditional Chinese for Taiwan:: The FreeBSD-Taiwan Project has a Chinese HOWTO for FreeBSD at http://netlab.cse.yzu.edu.tw/\~statue/freebsd/zh-tut/[http://netlab.cse.yzu.edu.tw/~statue/freebsd/zh-tut/]. Greek Language Localization:: A complete article on Greek support in FreeBSD is available https://www.FreeBSD.org/doc/gr/articles/greek-language-support/[here], in Greek only, as part of the official FreeBSD Greek documentation. Japanese and Korean Language Localization:: For Japanese, refer to http://www.jp.FreeBSD.org/[http://www.jp.FreeBSD.org/], and for Korean, refer to http://www.kr.FreeBSD.org/[http://www.kr.FreeBSD.org/]. Non-English FreeBSD Documentation:: -Some FreeBSD contributors have translated parts of the FreeBSD documentation to other languages. They are available through links on the link:https://www.FreeBSD.org/[FreeBSD web site] or in [.filename]#/usr/shared/doc#. +Some FreeBSD contributors have translated parts of the FreeBSD documentation to other languages. They are available through links on the link:https://www.FreeBSD.org/[FreeBSD web site] or in [.filename]#/usr/share/doc#. diff --git a/documentation/content/en/books/handbook/multimedia/_index.adoc b/documentation/content/en/books/handbook/multimedia/_index.adoc index 773d6a8bed..edd2f3f665 100644 --- a/documentation/content/en/books/handbook/multimedia/_index.adoc +++ b/documentation/content/en/books/handbook/multimedia/_index.adoc @@ -1,1071 +1,1071 @@ --- title: Chapter 7. Multimedia part: Part II. Common Tasks prev: books/handbook/desktop next: books/handbook/kernelconfig description: FreeBSD supports a wide variety of sound cards, allowing users to enjoy high fidelity output from a FreeBSD system tags: ["multimedia", "sound card", "MP3", "MythTV", "scanner", "SANE"] --- [[multimedia]] = Multimedia :doctype: book :toc: macro :toclevels: 1 :icons: font :sectnums: :sectnumlevels: 6 :source-highlighter: rouge :experimental: :skip-front-matter: :xrefstyle: basic :relfileprefix: ../ :outfilesuffix: :sectnumoffset: 7 ifeval::["{backend}" == "html5"] :imagesdir: ../../../../images/books/handbook/multimedia/ endif::[] ifeval::["{backend}" == "pdf"] :imagesdir: ../../../../static/images/books/handbook/multimedia/ endif::[] ifeval::["{backend}" == "epub3"] :imagesdir: ../../../../static/images/books/handbook/multimedia/ endif::[] include::shared/authors.adoc[] include::shared/releases.adoc[] include::shared/en/mailing-lists.adoc[] include::shared/en/teams.adoc[] include::shared/en/urls.adoc[] toc::[] [[multimedia-synopsis]] == Synopsis FreeBSD supports a wide variety of sound cards, allowing users to enjoy high fidelity output from a FreeBSD system. This includes the ability to record and play back audio in the MPEG Audio Layer 3 (`MP3`), Waveform Audio File (`WAV`), Ogg Vorbis, and other formats. The FreeBSD Ports Collection contains many applications for editing recorded audio, adding sound effects, and controlling attached MIDI devices. FreeBSD also supports the playback of video files and ``DVD``s. The FreeBSD Ports Collection contains applications to encode, convert, and playback various video media. This chapter describes how to configure sound cards, video playback, TV tuner cards, and scanners on FreeBSD. It also describes some of the applications which are available for using these devices. After reading this chapter, you will know how to: * Configure a sound card on FreeBSD. * Troubleshoot the sound setup. * Playback and encode MP3s and other audio. * Prepare a FreeBSD system for video playback. * Play ``DVD``s, [.filename]#.mpg#, and [.filename]#.avi# files. * Rip `CD` and `DVD` content into files. * Configure a TV card. * Install and setup MythTV on FreeBSD * Configure an image scanner. * Configure a Bluetooth headset. Before reading this chapter, you should: * Know how to install applications as described in crossref:ports[ports,Installing Applications: Packages and Ports]. [[sound-setup]] == Setting Up the Sound Card Before beginning the configuration, determine the model of the sound card and the chip it uses. FreeBSD supports a wide variety of sound cards. Check the supported audio devices list of the link:{u-rel120-hardware}[Hardware Notes] to see if the card is supported and which FreeBSD driver it uses. In order to use the sound device, its device driver must be loaded. The easiest way is to load a kernel module for the sound card with man:kldload[8]. This example loads the driver for a built-in audio chipset based on the Intel specification: [source,shell] .... # kldload snd_hda .... To automate the loading of this driver at boot time, add the driver to [.filename]#/boot/loader.conf#. The line for this driver is: [.programlisting] .... snd_hda_load="YES" .... Other available sound modules are listed in [.filename]#/boot/defaults/loader.conf#. When unsure which driver to use, load the [.filename]#snd_driver# module: [source,shell] .... # kldload snd_driver .... This is a metadriver which loads all of the most common sound drivers and can be used to speed up the search for the correct driver. It is also possible to load all sound drivers by adding the metadriver to [.filename]#/boot/loader.conf#. To determine which driver was selected for the sound card after loading the [.filename]#snd_driver# metadriver, type `cat /dev/sndstat`. === Configuring a Custom Kernel with Sound Support This section is for users who prefer to statically compile in support for the sound card in a custom kernel. For more information about recompiling a kernel, refer to crossref:kernelconfig[kernelconfig,Configuring the FreeBSD Kernel]. When using a custom kernel to provide sound support, make sure that the audio framework driver exists in the custom kernel configuration file: [.programlisting] .... device sound .... Next, add support for the sound card. To continue the example of the built-in audio chipset based on the Intel specification from the previous section, use the following line in the custom kernel configuration file: [.programlisting] .... device snd_hda .... Be sure to read the manual page of the driver for the device name to use for the driver. Non-PnP ISA sound cards may require the IRQ and I/O port settings of the card to be added to [.filename]#/boot/device.hints#. During the boot process, man:loader[8] reads this file and passes the settings to the kernel. For example, an old Creative SoundBlaster(R) 16 ISA non-PnP card will use the man:snd_sbc[4] driver in conjunction with `snd_sb16`. For this card, the following lines must be added to the kernel configuration file: [.programlisting] .... device snd_sbc device snd_sb16 .... If the card uses the `0x220` I/O port and IRQ `5`, these lines must also be added to [.filename]#/boot/device.hints#: [.programlisting] .... hint.sbc.0.at="isa" hint.sbc.0.port="0x220" hint.sbc.0.irq="5" hint.sbc.0.drq="1" hint.sbc.0.flags="0x15" .... The syntax used in [.filename]#/boot/device.hints# is described in man:sound[4] and the manual page for the driver of the sound card. The settings shown above are the defaults. In some cases, the IRQ or other settings may need to be changed to match the card. Refer to man:snd_sbc[4] for more information about this card. [[sound-testing]] === Testing Sound After loading the required module or rebooting into the custom kernel, the sound card should be detected. To confirm, run `dmesg | grep pcm`. This example is from a system with a built-in Conexant CX20590 chipset: [source,shell] .... pcm0: at nid 5 on hdaa0 pcm1: at nid 6 on hdaa0 pcm2: at nid 31,25 and 35,27 on hdaa1 .... The status of the sound card may also be checked using this command: [source,shell] .... # cat /dev/sndstat FreeBSD Audio Driver (newpcm: 64bit 2009061500/amd64) Installed devices: pcm0: (play) pcm1: (play) pcm2: (play/rec) default .... The output will vary depending upon the sound card. If no [.filename]#pcm# devices are listed, double-check that the correct device driver was loaded or compiled into the kernel. The next section lists some common problems and their solutions. If all goes well, the sound card should now work in FreeBSD. If the `CD` or `DVD` drive is properly connected to the sound card, one can insert an audio `CD` in the drive and play it with man:cdcontrol[1]: [source,shell] .... % cdcontrol -f /dev/acd0 play 1 .... [WARNING] ==== Audio ``CD``s have specialized encodings which means that they should not be mounted using man:mount[8]. ==== Various applications, such as package:audio/workman[], provide a friendlier interface. The package:audio/mpg123[] port can be installed to listen to MP3 audio files. Another quick way to test the card is to send data to [.filename]#/dev/dsp#: [source,shell] .... % cat filename > /dev/dsp .... where [.filename]#filename# can be any type of file. This command should produce some noise, confirming that the sound card is working. [NOTE] ==== The [.filename]#/dev/dsp*# device nodes will be created automatically as needed. When not in use, they do not exist and will not appear in the output of man:ls[1]. ==== [[bluetooth-headset]] === Setting up Bluetooth Sound Devices Connecting to a Bluetooth device is out of scope for this chapter. Refer to crossref:advanced-networking[network-bluetooth,“Bluetooth”] for more information. To get Bluetooth sound sink working with FreeBSD's sound system, users have to install package:audio/virtual_oss[] first: [source,shell] .... # pkg install virtual_oss .... package:audio/virtual_oss[] requires `cuse` to be loaded into the kernel: [source,shell] .... # kldload cuse .... To load `cuse` during system startup, run this command: [source,shell] .... # echo 'cuse_load=yes' >> /boot/loader.conf .... To use headphones as a sound sink with package:audio/virtual_oss[], users need to create a virtual device after connecting to a Bluetooth audio device: [source,shell] .... # virtual_oss -C 2 -c 2 -r 48000 -b 16 -s 768 -R /dev/null -P /dev/bluetooth/headphones -d dsp .... [NOTE] ==== _headphones_ in this example is a hostname from [.filename]#/etc/bluetooth/hosts#. `BT_ADDR` could be used instead. ==== Refer to man:virtual_oss[8] for more information. [[troubleshooting]] === Troubleshooting Sound <> lists some common error messages and their solutions: [[multimedia-sound-common-error-messages]] .Common Error Messages [cols="1,1", frame="none", options="header"] |=== | Error | Solution |`sb_dspwr(XX) timed out` | The I/O port is not set correctly. |`bad irq XX` | The IRQ is set incorrectly. Make sure that the set IRQ and the sound IRQ are the same. |`xxx: gus pcm not attached, out of memory` | There is not enough available memory to use the device. |`xxx: can't open /dev/dsp!` | Type `fstat \| grep` dsp to check if another application is holding the device open. Noteworthy troublemakers are esound and KDE's sound support. |=== Modern graphics cards often come with their own sound driver for use with `HDMI`. This sound device is sometimes enumerated before the sound card meaning that the sound card will not be used as the default playback device. To check if this is the case, run dmesg and look for `pcm`. The output looks something like this: [.programlisting] .... ... hdac0: HDA Driver Revision: 20100226_0142 hdac1: HDA Driver Revision: 20100226_0142 hdac0: HDA Codec #0: NVidia (Unknown) hdac0: HDA Codec #1: NVidia (Unknown) hdac0: HDA Codec #2: NVidia (Unknown) hdac0: HDA Codec #3: NVidia (Unknown) pcm0: at cad 0 nid 1 on hdac0 pcm1: at cad 1 nid 1 on hdac0 pcm2: at cad 2 nid 1 on hdac0 pcm3: at cad 3 nid 1 on hdac0 hdac1: HDA Codec #2: Realtek ALC889 pcm4: at cad 2 nid 1 on hdac1 pcm5: at cad 2 nid 1 on hdac1 pcm6: at cad 2 nid 1 on hdac1 pcm7: at cad 2 nid 1 on hdac1 ... .... In this example, the graphics card (`NVidia`) has been enumerated before the sound card (`Realtek ALC889`). To use the sound card as the default playback device, change `hw.snd.default_unit` to the unit that should be used for playback: [source,shell] .... # sysctl hw.snd.default_unit=n .... where `n` is the number of the sound device to use. In this example, it should be `4`. Make this change permanent by adding the following line to [.filename]#/etc/sysctl.conf#: [.programlisting] .... hw.snd.default_unit=4 .... [[sound-multiple-sources]] === Utilizing Multiple Sound Sources It is often desirable to have multiple sources of sound that are able to play simultaneously. FreeBSD uses "Virtual Sound Channels" to multiplex the sound card's playback by mixing sound in the kernel. Three man:sysctl[8] knobs are available for configuring virtual channels: [source,shell] .... # sysctl dev.pcm.0.play.vchans=4 # sysctl dev.pcm.0.rec.vchans=4 # sysctl hw.snd.maxautovchans=4 .... This example allocates four virtual channels, which is a practical number for everyday use. Both `dev.pcm.0.play.vchans=4` and `dev.pcm.0.rec.vchans=4` are configurable after a device has been attached and represent the number of virtual channels [.filename]#pcm0# has for playback and recording. Since the [.filename]#pcm# module can be loaded independently of the hardware drivers, `hw.snd.maxautovchans` indicates how many virtual channels will be given to an audio device when it is attached. Refer to man:pcm[4] for more information. [NOTE] ==== The number of virtual channels for a device cannot be changed while it is in use. First, close any programs using the device, such as music players or sound daemons. ==== The correct [.filename]#pcm# device will automatically be allocated transparently to a program that requests [.filename]#/dev/dsp0#. === Setting Default Values for Mixer Channels The default values for the different mixer channels are hardcoded in the source code of the man:pcm[4] driver. While sound card mixer levels can be changed using man:mixer[8] or third-party applications and daemons, this is not a permanent solution. To instead set default mixer values at the driver level, define the appropriate values in [.filename]#/boot/device.hints#, as seen in this example: [.programlisting] .... hint.pcm.0.vol="50" .... This will set the volume channel to a default value of `50` when the man:pcm[4] module is loaded. [[sound-mp3]] == MP3 Audio This section describes some `MP3` players available for FreeBSD, how to rip audio `CD` tracks, and how to encode and decode ``MP3``s. [[mp3-players]] === MP3 Players A popular graphical `MP3` player is Audacious. It supports Winamp skins and additional plugins. The interface is intuitive, with a playlist, graphic equalizer, and more. Those familiar with Winamp will find Audacious simple to use. On FreeBSD, Audacious can be installed from the package:multimedia/audacious[] port or package. Audacious is a descendant of XMMS. The package:audio/mpg123[] package or port provides an alternative, command-line `MP3` player. Once installed, specify the `MP3` file to play on the command line. If the system has multiple audio devices, the sound device can also be specified: [source,shell] .... # mpg123 -a /dev/dsp1.0 Foobar-GreatestHits.mp3 High Performance MPEG 1.0/2.0/2.5 Audio Player for Layers 1, 2 and 3 version 1.18.1; written and copyright by Michael Hipp and others free software (LGPL) without any warranty but with best wishes Playing MPEG stream from Foobar-GreatestHits.mp3 ... MPEG 1.0 layer III, 128 kbit/s, 44100 Hz joint-stereo .... Additional `MP3` players are available in the FreeBSD Ports Collection. [[rip-cd]] === Ripping `CD` Audio Tracks Before encoding a `CD` or `CD` track to `MP3`, the audio data on the `CD` must be ripped to the hard drive. This is done by copying the raw `CD` Digital Audio (`CDDA`) data to `WAV` files. The `cdda2wav` tool, which is installed with the package:sysutils/cdrtools[] suite, can be used to rip audio information from ``CD``s. With the audio `CD` in the drive, the following command can be issued as `root` to rip an entire `CD` into individual, per track, `WAV` files: [source,shell] .... # cdda2wav -D 0,1,0 -B .... In this example, the `-D _0,1,0_` indicates the `SCSI` device [.filename]#0,1,0# containing the `CD` to rip. Use `cdrecord -scanbus` to determine the correct device parameters for the system. To rip individual tracks, use `-t` to specify the track: [source,shell] .... # cdda2wav -D 0,1,0 -t 7 .... To rip a range of tracks, such as track one to seven, specify a range: [source,shell] .... # cdda2wav -D 0,1,0 -t 1+7 .... To rip from an `ATAPI` (`IDE`) `CDROM` drive, specify the device name in place of the `SCSI` unit numbers. For example, to rip track 7 from an IDE drive: [source,shell] .... # cdda2wav -D /dev/acd0 -t 7 .... Alternately, `dd` can be used to extract audio tracks on `ATAPI` drives, as described in crossref:disks[duplicating-audiocds,“Duplicating Audio CDs”]. [[mp3-encoding]] === Encoding and Decoding MP3s Lame is a popular `MP3` encoder which can be installed from the package:audio/lame[] port. Due to patent issues, a package is not available. The following command will convert the ripped `WAV` file [.filename]#audio01.wav# to [.filename]#audio01.mp3#: [source,shell] .... # lame -h -b 128 --tt "Foo Song Title" --ta "FooBar Artist" --tl "FooBar Album" \ --ty "2014" --tc "Ripped and encoded by Foo" --tg "Genre" audio01.wav audio01.mp3 .... The specified 128 kbits is a standard `MP3` bitrate while the 160 and 192 bitrates provide higher quality. The higher the bitrate, the larger the size of the resulting `MP3`. The `-h` turns on the "higher quality but a little slower" mode. The options beginning with `--t` indicate `ID3` tags, which usually contain song information, to be embedded within the `MP3` file. Additional encoding options can be found in the lame manual page. In order to burn an audio `CD` from ``MP3``s, they must first be converted to a non-compressed file format. XMMS can be used to convert to the `WAV` format, while mpg123 can be used to convert to the raw Pulse-Code Modulation (`PCM`) audio data format. To convert [.filename]#audio01.mp3# using mpg123, specify the name of the `PCM` file: [source,shell] .... # mpg123 -s audio01.mp3 > audio01.pcm .... To use XMMS to convert a `MP3` to `WAV` format, use these steps: [.procedure] .Procedure: Converting to `WAV` Format in XMMS . Launch XMMS. . Right-click the window to bring up the XMMS menu. . Select `Preferences` under `Options`. . Change the Output Plugin to "Disk Writer Plugin". . Press `Configure`. . Enter or browse to a directory to write the uncompressed files to. . Load the `MP3` file into XMMS as usual, with volume at 100% and EQ settings turned off. . Press `Play`. The XMMS will appear as if it is playing the `MP3`, but no music will be heard. It is actually playing the `MP3` to a file. . When finished, be sure to set the default Output Plugin back to what it was before in order to listen to ``MP3``s again. Both the `WAV` and `PCM` formats can be used with cdrecord. When using `WAV` files, there will be a small tick sound at the beginning of each track. This sound is the header of the `WAV` file. The package:audio/sox[] port or package can be used to remove the header: [source,shell] .... % sox -t wav -r 44100 -s -w -c 2 track.wav track.raw .... Refer to crossref:disks[creating-cds,“Creating and Using CD Media”] for more information on using a `CD` burner in FreeBSD. [[video-playback]] == Video Playback Before configuring video playback, determine the model and chipset of the video card. While Xorg supports a wide variety of video cards, not all provide good playback performance. To obtain a list of extensions supported by the Xorg server using the card, run `xdpyinfo` while Xorg is running. It is a good idea to have a short MPEG test file for evaluating various players and options. Since some `DVD` applications look for `DVD` media in [.filename]#/dev/dvd# by default, or have this device name hardcoded in them, it might be useful to make a symbolic link to the proper device: [source,shell] .... # ln -sf /dev/cd0 /dev/dvd .... Due to the nature of man:devfs[5], manually created links will not persist after a system reboot. In order to recreate the symbolic link automatically when the system boots, add the following line to [.filename]#/etc/devfs.conf#: [.programlisting] .... link cd0 dvd .... `DVD` decryption invokes certain functions that require write permission to the `DVD` device. To enhance the shared memory Xorg interface, it is recommended to increase the values of these man:sysctl[8] variables: [.programlisting] .... kern.ipc.shmmax=67108864 kern.ipc.shmall=32768 .... [[video-interface]] === Determining Video Capabilities There are several possible ways to display video under Xorg and what works is largely hardware dependent. Each method described below will have varying quality across different hardware. Common video interfaces include: . Xorg: normal output using shared memory. . XVideo: an extension to the Xorg interface which allows video to be directly displayed in drawable objects through a special acceleration. This extension provides good quality playback even on low-end machines. The next section describes how to determine if this extension is running. . `SDL`: the Simple Directmedia Layer is a porting layer for many operating systems, allowing cross-platform applications to be developed which make efficient use of sound and graphics. `SDL` provides a low-level abstraction to the hardware which can sometimes be more efficient than the Xorg interface. On FreeBSD, `SDL` can be installed using the package:devel/sdl20[] package or port. . `DGA`: the Direct Graphics Access is an Xorg extension which allows a program to bypass the Xorg server and directly alter the framebuffer. As it relies on a low-level memory mapping, programs using it must be run as `root`. The `DGA` extension can be tested and benchmarked using man:dga[1]. When `dga` is running, it changes the colors of the display whenever a key is pressed. To quit, press kbd:[q]. . SVGAlib: a low level console graphics layer. [[video-interface-xvideo]] ==== XVideo To check whether this extension is running, use `xvinfo`: [source,shell] .... % xvinfo .... XVideo is supported for the card if the result is similar to: [source,shell] .... X-Video Extension version 2.2 screen #0 Adaptor #0: "Savage Streams Engine" number of ports: 1 port base: 43 operations supported: PutImage supported visuals: depth 16, visualID 0x22 depth 16, visualID 0x23 number of attributes: 5 "XV_COLORKEY" (range 0 to 16777215) client settable attribute client gettable attribute (current value is 2110) "XV_BRIGHTNESS" (range -128 to 127) client settable attribute client gettable attribute (current value is 0) "XV_CONTRAST" (range 0 to 255) client settable attribute client gettable attribute (current value is 128) "XV_SATURATION" (range 0 to 255) client settable attribute client gettable attribute (current value is 128) "XV_HUE" (range -180 to 180) client settable attribute client gettable attribute (current value is 0) maximum XvImage size: 1024 x 1024 Number of image formats: 7 id: 0x32595559 (YUY2) guid: 59555932-0000-0010-8000-00aa00389b71 bits per pixel: 16 number of planes: 1 type: YUV (packed) id: 0x32315659 (YV12) guid: 59563132-0000-0010-8000-00aa00389b71 bits per pixel: 12 number of planes: 3 type: YUV (planar) id: 0x30323449 (I420) guid: 49343230-0000-0010-8000-00aa00389b71 bits per pixel: 12 number of planes: 3 type: YUV (planar) id: 0x36315652 (RV16) guid: 52563135-0000-0000-0000-000000000000 bits per pixel: 16 number of planes: 1 type: RGB (packed) depth: 0 red, green, blue masks: 0x1f, 0x3e0, 0x7c00 id: 0x35315652 (RV15) guid: 52563136-0000-0000-0000-000000000000 bits per pixel: 16 number of planes: 1 type: RGB (packed) depth: 0 red, green, blue masks: 0x1f, 0x7e0, 0xf800 id: 0x31313259 (Y211) guid: 59323131-0000-0010-8000-00aa00389b71 bits per pixel: 6 number of planes: 3 type: YUV (packed) id: 0x0 guid: 00000000-0000-0000-0000-000000000000 bits per pixel: 0 number of planes: 0 type: RGB (packed) depth: 1 red, green, blue masks: 0x0, 0x0, 0x0 .... The formats listed, such as YUV2 and YUV12, are not present with every implementation of XVideo and their absence may hinder some players. If the result instead looks like: [source,shell] .... X-Video Extension version 2.2 screen #0 no adaptors present .... XVideo is probably not supported for the card. This means that it will be more difficult for the display to meet the computational demands of rendering video, depending on the video card and processor. [[video-ports]] === Ports and Packages Dealing with Video This section introduces some of the software available from the FreeBSD Ports Collection which can be used for video playback. [[video-mplayer]] ==== MPlayer and MEncoder MPlayer is a command-line video player with an optional graphical interface which aims to provide speed and flexibility. Other graphical front-ends to MPlayer are available from the FreeBSD Ports Collection. MPlayer can be installed using the package:multimedia/mplayer[] package or port. Several compile options are available and a variety of hardware checks occur during the build process. For these reasons, some users prefer to build the port rather than install the package. When compiling the port, the menu options should be reviewed to determine the type of support to compile into the port. If an option is not selected, MPlayer will not be able to display that type of video format. Use the arrow keys and spacebar to select the required formats. When finished, press kbd:[Enter] to continue the port compile and installation. By default, the package or port will build the `mplayer` command line utility and the `gmplayer` graphical utility. To encode videos, compile the package:multimedia/mencoder[] port. Due to licensing restrictions, a package is not available for MEncoder. The first time MPlayer is run, it will create [.filename]#~/.mplayer# in the user's home directory. This subdirectory contains default versions of the user-specific configuration files. This section describes only a few common uses. Refer to mplayer(1) for a complete description of its numerous options. To play the file [.filename]#testfile.avi#, specify the video interfaces with `-vo`, as seen in the following examples: [source,shell] .... % mplayer -vo xv testfile.avi .... [source,shell] .... % mplayer -vo sdl testfile.avi .... [source,shell] .... % mplayer -vo x11 testfile.avi .... [source,shell] .... # mplayer -vo dga testfile.avi .... [source,shell] .... # mplayer -vo 'sdl:dga' testfile.avi .... It is worth trying all of these options, as their relative performance depends on many factors and will vary significantly with hardware. To play a `DVD`, replace [.filename]#testfile.avi# with `dvd://_N_ -dvd-device _DEVICE_`, where _N_ is the title number to play and _DEVICE_ is the device node for the `DVD`. For example, to play title 3 from [.filename]#/dev/dvd#: [source,shell] .... # mplayer -vo xv dvd://3 -dvd-device /dev/dvd .... [NOTE] ==== The default `DVD` device can be defined during the build of the MPlayer port by including the `WITH_DVD_DEVICE=/path/to/desired/device` option. By default, the device is [.filename]#/dev/cd0#. More details can be found in the port's [.filename]#Makefile.options#. ==== To stop, pause, advance, and so on, use a keybinding. To see the list of keybindings, run `mplayer -h` or read mplayer(1). Additional playback options include `-fs -zoom`, which engages fullscreen mode, and `-framedrop`, which helps performance. Each user can add commonly used options to their [.filename]#~/.mplayer/config# like so: [.programlisting] .... vo=xv fs=yes zoom=yes .... `mplayer` can be used to rip a `DVD` title to a [.filename]#.vob#. To dump the second title from a `DVD`: [source,shell] .... # mplayer -dumpstream -dumpfile out.vob dvd://2 -dvd-device /dev/dvd .... The output file, [.filename]#out.vob#, will be in `MPEG` format. Anyone wishing to obtain a high level of expertise with UNIX(R) video should consult http://www.mplayerhq.hu/DOCS/[mplayerhq.hu/DOCS] as it is technically informative. This documentation should be considered as required reading before submitting any bug reports. Before using `mencoder`, it is a good idea to become familiar with the options described at http://www.mplayerhq.hu/DOCS/HTML/en/mencoder.html[mplayerhq.hu/DOCS/HTML/en/mencoder.html]. There are innumerable ways to improve quality, lower bitrate, and change formats, and some of these options may make the difference between good or bad performance. Improper combinations of command line options can yield output files that are unplayable even by `mplayer`. Here is an example of a simple copy: [source,shell] .... % mencoder input.avi -oac copy -ovc copy -o output.avi .... To rip to a file, use `-dumpfile` with `mplayer`. To convert [.filename]#input.avi# to the MPEG4 codec with MPEG3 audio encoding, first install the package:audio/lame[] port. Due to licensing restrictions, a package is not available. Once installed, type: [source,shell] .... % mencoder input.avi -oac mp3lame -lameopts br=192 \ -ovc lavc -lavcopts vcodec=mpeg4:vhq -o output.avi .... This will produce output playable by applications such as `mplayer` and `xine`. [.filename]#input.avi# can be replaced with `dvd://1 -dvd-device /dev/dvd` and run as `root` to re-encode a `DVD` title directly. Since it may take a few tries to get the desired result, it is recommended to instead dump the title to a file and to work on the file. [[video-xine]] ==== The xine Video Player xine is a video player with a reusable base library and a modular executable which can be extended with plugins. It can be installed using the package:multimedia/xine[] package or port. In practice, xine requires either a fast CPU with a fast video card, or support for the XVideo extension. The xine video player performs best on XVideo interfaces. By default, the xine player starts a graphical user interface. The menus can then be used to open a specific file. Alternatively, xine may be invoked from the command line by specifying the name of the file to play: [source,shell] .... % xine -g -p mymovie.avi .... Refer to http://www.xine-project.org/faq[xine-project.org/faq] for more information and troubleshooting tips. [[video-ports-transcode]] ==== The Transcode Utilities Transcode provides a suite of tools for re-encoding video and audio files. Transcode can be used to merge video files or repair broken files using command line tools with stdin/stdout stream interfaces. In FreeBSD, Transcode can be installed using the package:multimedia/transcode[] package or port. Many users prefer to compile the port as it provides a menu of compile options for specifying the support and codecs to compile in. If an option is not selected, Transcode will not be able to encode that format. Use the arrow keys and spacebar to select the required formats. When finished, press kbd:[Enter] to continue the port compile and installation. This example demonstrates how to convert a DivX file into a PAL MPEG-1 file (PAL VCD): [source,shell] .... % transcode -i input.avi -V --export_prof vcd-pal -o output_vcd % mplex -f 1 -o output_vcd.mpg output_vcd.m1v output_vcd.mpa .... The resulting `MPEG` file, [.filename]#output_vcd.mpg#, is ready to be played with MPlayer. The file can be burned on a `CD` media to create a video `CD` using a utility such as package:multimedia/vcdimager[] or package:sysutils/cdrdao[]. In addition to the manual page for `transcode`, refer to http://www.transcoding.org/cgi-bin/transcode[transcoding.org/cgi-bin/transcode] for further information and examples. [[tvcard]] == TV Cards TV cards can be used to watch broadcast or cable TV on a computer. Most cards accept composite video via an `RCA` or S-video input and some cards include a `FM` radio tuner. FreeBSD provides support for PCI-based TV cards using a Brooktree Bt848/849/878/879 video capture chip with the man:bktr[4] driver. This driver supports most Pinnacle PCTV video cards. Before purchasing a TV card, consult man:bktr[4] for a list of supported tuners. === Loading the Driver In order to use the card, the man:bktr[4] driver must be loaded. To automate this at boot time, add the following line to [.filename]#/boot/loader.conf#: [.programlisting] .... bktr_load="YES" .... Alternatively, one can statically compile support for the TV card into a custom kernel. In that case, add the following lines to the custom kernel configuration file: [.programlisting] .... device bktr device iicbus device iicbb device smbus .... These additional devices are necessary as the card components are interconnected via an I2C bus. Then, build and install a new kernel. To test that the tuner is correctly detected, reboot the system. The TV card should appear in the boot messages, as seen in this example: [.programlisting] .... bktr0: mem 0xd7000000-0xd7000fff irq 10 at device 10.0 on pci0 iicbb0: on bti2c0 iicbus0: on iicbb0 master-only iicbus1: on iicbb0 master-only smbus0: on bti2c0 bktr0: Pinnacle/Miro TV, Philips SECAM tuner. .... The messages will differ according to the hardware. If necessary, it is possible to override some of the detected parameters using man:sysctl[8] or custom kernel configuration options. For example, to force the tuner to a Philips SECAM tuner, add the following line to a custom kernel configuration file: [.programlisting] .... options OVERRIDE_TUNER=6 .... or, use man:sysctl[8]: [source,shell] .... # sysctl hw.bt848.tuner=6 .... Refer to man:bktr[4] for a description of the available man:sysctl[8] parameters and kernel options. === Useful Applications To use the TV card, install one of the following applications: * package:multimedia/fxtv[] provides TV-in-a-window and image/audio/video capture capabilities. * package:multimedia/xawtv[] is another TV application with similar features. * package:audio/xmradio[] provides an application for using the FM radio tuner of a TV card. More applications are available in the FreeBSD Ports Collection. === Troubleshooting If any problems are encountered with the TV card, check that the video capture chip and the tuner are supported by man:bktr[4] and that the right configuration options were used. For more support or to ask questions about supported TV cards, refer to the {freebsd-multimedia} mailing list. [[mythtv]] == MythTV MythTV is a popular, open source Personal Video Recorder (`PVR`) application. This section demonstrates how to install and setup MythTV on FreeBSD. Refer to http://www.mythtv.org/wiki/[mythtv.org/wiki] for more information on how to use MythTV. MythTV requires a frontend and a backend. These components can either be installed on the same system or on different machines. The frontend can be installed on FreeBSD using the package:multimedia/mythtv-frontend[] package or port. Xorg must also be installed and configured as described in crossref:x11[x11,The X Window System]. Ideally, this system has a video card that supports X-Video Motion Compensation (`XvMC`) and, optionally, a Linux Infrared Remote Control (`LIRC`)-compatible remote. To install both the backend and the frontend on FreeBSD, use the package:multimedia/mythtv[] package or port. A MySQL(TM) database server is also required and should automatically be installed as a dependency. Optionally, this system should have a tuner card and sufficient storage to hold recorded data. === Hardware MythTV uses Video for Linux (`V4L`) to access video input devices such as encoders and tuners. In FreeBSD, MythTV works best with `USB` DVB-S/C/T cards as they are well supported by the package:multimedia/webcamd[] package or port which provides a `V4L` userland application. Any Digital Video Broadcasting (`DVB`) card supported by webcamd should work with MythTV. A list of known working cards can be found at https://wiki.freebsd.org/WebcamCompat[wiki.freebsd.org/WebcamCompat]. Drivers are also available for Hauppauge cards in the package:multimedia/pvr250[] and package:multimedia/pvrxxx[] ports, but they provide a non-standard driver interface that does not work with versions of MythTV greater than 0.23. Due to licensing restrictions, no packages are available and these two ports must be compiled. The https://wiki.freebsd.org/HTPC[wiki.freebsd.org/HTPC] page contains a list of all available `DVB` drivers. === Setting up the MythTV Backend To install MythTV using binary packages: [source,shell] .... # pkg install mythtv .... Alternatively, to install from the Ports Collection: [source,shell] .... # cd /usr/ports/multimedia/mythtv # make install .... Once installed, set up the MythTV database: [source,shell] .... -# mysql -uroot -p < /usr/local/shared/mythtv/database/mc.sql +# mysql -uroot -p < /usr/local/share/mythtv/database/mc.sql .... Then, configure the backend: [source,shell] .... # mythtv-setup .... Finally, start the backend: [source,shell] .... # sysrc mythbackend_enable=yes # service mythbackend start .... [[scanners]] == Image Scanners In FreeBSD, access to image scanners is provided by SANE (Scanner Access Now Easy), which is available in the FreeBSD Ports Collection. SANE will also use some FreeBSD device drivers to provide access to the scanner hardware. FreeBSD supports both `SCSI` and `USB` scanners. Depending upon the scanner interface, different device drivers are required. Be sure the scanner is supported by SANE prior to performing any configuration. Refer to http://www.sane-project.org/sane-supported-devices.html[http://www.sane-project.org/sane-supported-devices.html] for more information about supported scanners. This chapter describes how to determine if the scanner has been detected by FreeBSD. It then provides an overview of how to configure and use SANE on a FreeBSD system. [[scanners-kernel-usb]] === Checking the Scanner The [.filename]#GENERIC# kernel includes the device drivers needed to support `USB` scanners. Users with a custom kernel should ensure that the following lines are present in the custom kernel configuration file: [.programlisting] .... device usb device uhci device ohci device ehci device xhci .... To determine if the `USB` scanner is detected, plug it in and use `dmesg` to determine whether the scanner appears in the system message buffer. If it does, it should display a message similar to this: [source,shell] .... ugen0.2: at usbus0 .... In this example, an EPSON Perfection(R) 1650 `USB` scanner was detected on [.filename]#/dev/ugen0.2#. If the scanner uses a `SCSI` interface, it is important to know which `SCSI` controller board it will use. Depending upon the `SCSI` chipset, a custom kernel configuration file may be needed. The [.filename]#GENERIC# kernel supports the most common `SCSI` controllers. Refer to [.filename]#/usr/src/sys/conf/NOTES# to determine the correct line to add to a custom kernel configuration file. In addition to the `SCSI` adapter driver, the following lines are needed in a custom kernel configuration file: [.programlisting] .... device scbus device pass .... Verify that the device is displayed in the system message buffer: [source,shell] .... pass2 at aic0 bus 0 target 2 lun 0 pass2: Fixed Scanner SCSI-2 device pass2: 3.300MB/s transfers .... If the scanner was not powered-on at system boot, it is still possible to manually force detection by performing a `SCSI` bus scan with `camcontrol`: [source,shell] .... # camcontrol rescan all Re-scan of bus 0 was successful Re-scan of bus 1 was successful Re-scan of bus 2 was successful Re-scan of bus 3 was successful .... The scanner should now appear in the `SCSI` devices list: [source,shell] .... # camcontrol devlist at scbus0 target 5 lun 0 (pass0,da0) at scbus0 target 6 lun 0 (pass1,da1) at scbus1 target 2 lun 0 (pass3) at scbus2 target 0 lun 0 (pass2,cd0) .... Refer to man:scsi[4] and man:camcontrol[8] for more details about `SCSI` devices on FreeBSD. === SANE Configuration The SANE system provides the access to the scanner via backends (package:graphics/sane-backends[]). Refer to http://www.sane-project.org/sane-supported-devices.html[http://www.sane-project.org/sane-supported-devices.html] to determine which backend supports the scanner. A graphical scanning interface is provided by third party applications like Kooka (package:graphics/kooka[]) or XSane (package:graphics/xsane[]). SANE's backends are enough to test the scanner. To install the backends from binary package: [source,shell] .... # pkg install sane-backends .... Alternatively, to install from the Ports Collection [source,shell] .... # cd /usr/ports/graphics/sane-backends # make install clean .... After installing the package:graphics/sane-backends[] port or package, use `sane-find-scanner` to check the scanner detection by the SANE system: [source,shell] .... # sane-find-scanner -q found SCSI scanner "AGFA SNAPSCAN 600 1.10" at /dev/pass3 .... The output should show the interface type of the scanner and the device node used to attach the scanner to the system. The vendor and the product model may or may not appear. [NOTE] ==== Some `USB` scanners require firmware to be loaded. Refer to sane-find-scanner(1) and sane(7) for details. ==== Next, check if the scanner will be identified by a scanning frontend. The SANE backends include `scanimage` which can be used to list the devices and perform an image acquisition. Use `-L` to list the scanner devices. The first example is for a `SCSI` scanner and the second is for a `USB` scanner: [source,shell] .... # scanimage -L device `snapscan:/dev/pass3' is a AGFA SNAPSCAN 600 flatbed scanner # scanimage -L device 'epson2:libusb:000:002' is a Epson GT-8200 flatbed scanner .... In this second example, `epson2` is the backend name and `libusb:000:002` means [.filename]#/dev/ugen0.2# is the device node used by the scanner. If `scanimage` is unable to identify the scanner, this message will appear: [source,shell] .... # scanimage -L No scanners were identified. If you were expecting something different, check that the scanner is plugged in, turned on and detected by the sane-find-scanner tool (if appropriate). Please read the documentation which came with this software (README, FAQ, manpages). .... If this happens, edit the backend configuration file in [.filename]#/usr/local/etc/sane.d/# and define the scanner device used. For example, if the undetected scanner model is an EPSON Perfection(R) 1650 and it uses the `epson2` backend, edit [.filename]#/usr/local/etc/sane.d/epson2.conf#. When editing, add a line specifying the interface and the device node used. In this case, add the following line: [.programlisting] .... usb /dev/ugen0.2 .... Save the edits and verify that the scanner is identified with the right backend name and the device node: [source,shell] .... # scanimage -L device 'epson2:libusb:000:002' is a Epson GT-8200 flatbed scanner .... Once `scanimage -L` sees the scanner, the configuration is complete and the scanner is now ready to use. While `scanimage` can be used to perform an image acquisition from the command line, it is often preferable to use a graphical interface to perform image scanning. Applications like Kooka or XSane are popular scanning frontends. They offer advanced features such as various scanning modes, color correction, and batch scans. XSane is also usable as a GIMP plugin. === Scanner Permissions In order to have access to the scanner, a user needs read and write permissions to the device node used by the scanner. In the previous example, the `USB` scanner uses the device node [.filename]#/dev/ugen0.2# which is really a symlink to the real device node [.filename]#/dev/usb/0.2.0#. The symlink and the device node are owned, respectively, by the `wheel` and `operator` groups. While adding the user to these groups will allow access to the scanner, it is considered insecure to add a user to `wheel`. A better solution is to create a group and make the scanner device accessible to members of this group. This example creates a group called `_usb_`: [source,shell] .... # pw groupadd usb .... Then, make the [.filename]#/dev/ugen0.2# symlink and the [.filename]#/dev/usb/0.2.0# device node accessible to the `usb` group with write permissions of `0660` or `0664` by adding the following lines to [.filename]#/etc/devfs.rules#: [.programlisting] .... [system=5] add path ugen0.2 mode 0660 group usb add path usb/0.2.0 mode 0666 group usb .... [NOTE] ==== It happens the device node changes with the addition or removal of devices, so one may want to give access to all USB devices using this ruleset instead: [.programlisting] .... [system=5] add path 'ugen*' mode 0660 group usb add path 'usb/*' mode 0666 group usb .... ==== Refer to man:devfs.rules[5] for more information about this file. Next, enable the ruleset in /etc/rc.conf: [.programlisting] .... devfs_system_ruleset="system" .... And, restart the man:devfs[8] system: [source,shell] .... # service devfs restart .... Finally, add the users to `_usb_` in order to allow access to the scanner: [source,shell] .... # pw groupmod usb -m joe .... For more details refer to man:pw[8]. diff --git a/documentation/content/en/books/handbook/ports/_index.adoc b/documentation/content/en/books/handbook/ports/_index.adoc index d39d36127d..b263d8d3e5 100644 --- a/documentation/content/en/books/handbook/ports/_index.adoc +++ b/documentation/content/en/books/handbook/ports/_index.adoc @@ -1,1174 +1,1174 @@ --- title: "Chapter 4. Installing Applications: Packages and Ports" part: Part I. Getting Started prev: books/handbook/basics next: books/handbook/x11 description: "FreeBSD provides two complementary technologies for installing third-party software: the FreeBSD Ports Collection, for installing from source, and packages, for installing from pre-built binaries" tags: ["ports", "collection", "pkg", "poudriere", "management"] --- [[ports]] = Installing Applications: Packages and Ports :doctype: book :toc: macro :toclevels: 1 :icons: font :sectnums: :sectnumlevels: 6 :source-highlighter: rouge :experimental: :skip-front-matter: :xrefstyle: basic :relfileprefix: ../ :outfilesuffix: :sectnumoffset: 4 ifeval::["{backend}" == "html5"] :imagesdir: ../../../../images/books/handbook/ports/ endif::[] ifeval::["{backend}" == "pdf"] :imagesdir: ../../../../static/images/books/handbook/ports/ endif::[] ifeval::["{backend}" == "epub3"] :imagesdir: ../../../../static/images/books/handbook/ports/ endif::[] include::shared/authors.adoc[] include::shared/releases.adoc[] include::shared/en/mailing-lists.adoc[] include::shared/en/teams.adoc[] include::shared/en/urls.adoc[] toc::[] [[ports-synopsis]] == Synopsis FreeBSD is bundled with a rich collection of system tools as part of the base system. In addition, FreeBSD provides two complementary technologies for installing third-party software: the FreeBSD Ports Collection, for installing from source, and packages, for installing from pre-built binaries. Either method may be used to install software from local media or from the network. After reading this chapter, you will know: * The difference between binary packages and ports. * How to find third-party software that has been ported to FreeBSD. * How to manage binary packages using pkg. * How to build third-party software from source using the Ports Collection. * How to find the files installed with the application for post-installation configuration. * What to do if a software installation fails. [[ports-overview]] == Overview of Software Installation The typical steps for installing third-party software on a UNIX(R) system include: [.procedure] . Find and download the software, which might be distributed in source code format or as a binary. . Unpack the software from its distribution format. This is typically a tarball compressed with a program such as man:compress[1], man:gzip[1], man:bzip2[1] or man:xz[1]. . Locate the documentation in [.filename]#INSTALL#, [.filename]#README# or some file in a [.filename]#doc/# subdirectory and read up on how to install the software. . If the software was distributed in source format, compile it. This may involve editing a [.filename]#Makefile# or running a `configure` script. . Test and install the software. A FreeBSD _port_ is a collection of files designed to automate the process of compiling an application from source code. The files that comprise a port contain all the necessary information to automatically download, extract, patch, compile, and install the application. If the software has not already been adapted and tested on FreeBSD, the source code might need editing in order for it to install and run properly. However, over link:https://www.FreeBSD.org/ports/[{numports}] third-party applications have already been ported to FreeBSD. When feasible, these applications are made available for download as pre-compiled _packages_. Packages can be manipulated with the FreeBSD package management commands. Both packages and ports understand dependencies. If a package or port is used to install an application and a dependent library is not already installed, the library will automatically be installed first. A FreeBSD package contains pre-compiled copies of all the commands for an application, as well as any configuration files and documentation. A package can be manipulated with the man:pkg[8] commands, such as `pkg install`. While the two technologies are similar, packages and ports each have their own strengths. Select the technology that meets your requirements for installing a particular application. .Package Benefits * A compressed package tarball is typically smaller than the compressed tarball containing the source code for the application. * Packages do not require compilation time. For large applications, such as Mozilla, KDE, or GNOME, this can be important on a slow system. * Packages do not require any understanding of the process involved in compiling software on FreeBSD. .Port Benefits * Packages are normally compiled with conservative options because they have to run on the maximum number of systems. By compiling from the port, one can change the compilation options. * Some applications have compile-time options relating to which features are installed. For example, Apache can be configured with a wide variety of different built-in options. + In some cases, multiple packages will exist for the same application to specify certain settings. For example, Ghostscript is available as a [.filename]#ghostscript# package and a [.filename]#ghostscript-nox11# package, depending on whether or not Xorg is installed. Creating multiple packages rapidly becomes impossible if an application has more than one or two different compile-time options. * The licensing conditions of some software forbid binary distribution. Such software must be distributed as source code which must be compiled by the end-user. * Some people do not trust binary distributions or prefer to read through source code in order to look for potential problems. * Source code is needed in order to apply custom patches. To keep track of updated ports, subscribe to the {freebsd-ports} and the {freebsd-ports-bugs}. [WARNING] ==== Before installing any application, check https://vuxml.freebsd.org/[] for security issues related to the application or type `pkg audit -F` to check all installed applications for known vulnerabilities. ==== The remainder of this chapter explains how to use packages and ports to install and manage third-party software on FreeBSD. [[ports-finding-applications]] == Finding Software FreeBSD's list of available applications is growing all the time. There are a number of ways to find software to install: * The FreeBSD web site maintains an up-to-date searchable list of all the available applications, at link:https://www.FreeBSD.org/ports/[https://www.FreeBSD.org/ports/]. The ports can be searched by application name or by software category. * Dan Langille maintains http://www.FreshPorts.org/[FreshPorts.org] which provides a comprehensive search utility and also tracks changes to the applications in the Ports Collection. Registered users can create a customized watch list in order to receive an automated email when their watched ports are updated. * If finding a particular application becomes challenging, try searching a site like http://www.sourceforge.net/[SourceForge.net] or http://www.github.com/[GitHub.com] then check back at the link:https://www.FreeBSD.org/ports/[FreeBSD site] to see if the application has been ported. * To search the binary package repository for an application: + [source,shell] .... # pkg search subversion git-subversion-1.9.2 java-subversion-1.8.8_2 p5-subversion-1.8.8_2 py27-hgsubversion-1.6 py27-subversion-1.8.8_2 ruby-subversion-1.8.8_2 subversion-1.8.8_2 subversion-book-4515 subversion-static-1.8.8_2 subversion16-1.6.23_4 subversion17-1.7.16_2 .... + Package names include the version number and, in the case of ports based on python, the version number of the version of python the package was built with. Some ports also have multiple versions available. In the case of Subversion, there are different versions available, as well as different compile options. In this case, the statically linked version of Subversion. When indicating which package to install, it is best to specify the application by the port origin, which is the path in the ports tree. Repeat the `pkg search` with `-o` to list the origin of each package: + [source,shell] .... # pkg search -o subversion devel/git-subversion java/java-subversion devel/p5-subversion devel/py-hgsubversion devel/py-subversion devel/ruby-subversion devel/subversion16 devel/subversion17 devel/subversion devel/subversion-book devel/subversion-static .... + Searching by shell globs, regular expressions, exact match, by description, or any other field in the repository database is also supported by `pkg search`. After installing package:ports-mgmt/pkg[] or package:ports-mgmt/pkg-devel[], see man:pkg-search[8] for more details. * If the Ports Collection is already installed, there are several methods to query the local version of the ports tree. To find out which category a port is in, type `whereis _file_`, where _file_ is the program to be installed: + [source,shell] .... # whereis lsof lsof: /usr/ports/sysutils/lsof .... + Alternately, an man:echo[1] statement can be used: + [source,shell] .... # echo /usr/ports/*/*lsof* /usr/ports/sysutils/lsof .... + Note that this will also return any matched files downloaded into the [.filename]#/usr/ports/distfiles# directory. * Another way to find software is by using the Ports Collection's built-in search mechanism. To use the search feature, cd to [.filename]#/usr/ports# then run `make search name=program-name` where _program-name_ is the name of the software. For example, to search for `lsof`: + [source,shell] .... # cd /usr/ports # make search name=lsof Port: lsof-4.88.d,8 Path: /usr/ports/sysutils/lsof Info: Lists information about open files (similar to fstat(1)) Maint: ler@lerctr.org Index: sysutils B-deps: R-deps: .... + [TIP] ==== The built-in search mechanism uses a file of index information. If a message indicates that the [.filename]#INDEX# is required, run `make fetchindex` to download the current index file. With the [.filename]#INDEX# present, `make search` will be able to perform the requested search. ==== + The "Path:" line indicates where to find the port. + To receive less information, use the `quicksearch` feature: + [source,shell] .... # cd /usr/ports # make quicksearch name=lsof Port: lsof-4.88.d,8 Path: /usr/ports/sysutils/lsof Info: Lists information about open files (similar to fstat(1)) .... + For more in-depth searching, use `make search key=_string_` or `make quicksearch key=_string_`, where _string_ is some text to search for. The text can be in comments, descriptions, or dependencies in order to find ports which relate to a particular subject when the name of the program is unknown. + When using `search` or `quicksearch`, the search string is case-insensitive. Searching for "LSOF" will yield the same results as searching for "lsof". [[pkgng-intro]] == Using pkg for Binary Package Management pkg is the next generation replacement for the traditional FreeBSD package management tools, offering many features that make dealing with binary packages faster and easier. For sites wishing to only use prebuilt binary packages from the FreeBSD mirrors, managing packages with pkg can be sufficient. However, for those sites building from source or using their own repositories, a separate <> will be needed. Since pkg only works with binary packages, it is not a replacement for such tools. Those tools can be used to install software from both binary packages and the Ports Collection, while pkg installs only binary packages. [[pkgng-initial-setup]] === Getting Started with pkg FreeBSD includes a bootstrap utility which can be used to download and install pkg and its manual pages. This utility is designed to work with versions of FreeBSD starting with 10._X_. [NOTE] ==== Not all FreeBSD versions and architectures support this bootstrap process. The current list is at https://pkg.freebsd.org/[]. For other cases, pkg must instead be installed from the Ports Collection or as a binary package. ==== To bootstrap the system, run: [source,shell] .... # /usr/sbin/pkg .... You must have a working Internet connection for the bootstrap process to succeed. Otherwise, to install the port, run: [source,shell] .... # cd /usr/ports/ports-mgmt/pkg # make # make install clean .... When upgrading an existing system that originally used the older pkg_* tools, the database must be converted to the new format, so that the new tools are aware of the already installed packages. Once pkg has been installed, the package database must be converted from the traditional format to the new format by running this command: [source,shell] .... # pkg2ng .... [NOTE] ==== This step is not required for new installations that do not yet have any third-party software installed. ==== [IMPORTANT] ==== This step is not reversible. Once the package database has been converted to the pkg format, the traditional `pkg_*` tools should no longer be used. ==== [NOTE] ==== The package database conversion may emit errors as the contents are converted to the new version. Generally, these errors can be safely ignored. However, a list of software that was not successfully converted is shown after `pkg2ng` finishes. These applications must be manually reinstalled. ==== To ensure that the Ports Collection registers new software with pkg instead of the traditional packages database, FreeBSD versions earlier than 10._X_ require this line in [.filename]#/etc/make.conf#: [.programlisting] .... WITH_PKGNG= yes .... By default, pkg uses the binary packages from the FreeBSD package mirrors (the _repository_). For information about building a custom package repository, see <>. Additional pkg configuration options are described in man:pkg.conf[5]. Usage information for pkg is available in the man:pkg[8] manual page or by running `pkg` without additional arguments. Each pkg command argument is documented in a command-specific manual page. To read the manual page for `pkg install`, for example, run either of these commands: [source,shell] .... # pkg help install .... [source,shell] .... # man pkg-install .... The rest of this section demonstrates common binary package management tasks which can be performed using pkg. Each demonstrated command provides many switches to customize its use. Refer to a command's help or man page for details and more examples. [[quarterly-latest-branch]] === Quarterly and Latest Ports Branches The `Quarterly` branch provides users with a more predictable and stable experience for port and package installation and upgrades. This is done essentially by only allowing non-feature updates. Quarterly branches aim to receive security fixes (that may be version updates, or backports of commits), bug fixes and ports compliance or framework changes. The Quarterly branch is cut from HEAD at the beginning of every (yearly) quarter in January, April, July, and October. Branches are named according to the year (YYYY) and quarter (Q1-4) they are created in. For example, the quarterly branch created in January 2016, is named 2016Q1. And the `Latest` branch provides the latest versions of the packages to the users. To switch from quarterly to latest run the following commands: [source,shell] .... # mkdir -p /usr/local/etc/pkg/repos # cp /etc/pkg/FreeBSD.conf /usr/local/etc/pkg/repos/FreeBSD.conf .... Edit the file [.filename]#/usr/local/etc/pkg/repos/FreeBSD.conf# and change the string _quarterly_ to _latest_ in the `url:` line. The result should be similar to the following: [.programlisting] .... FreeBSD: { url: "pkg+http://pkg.FreeBSD.org/${ABI}/latest", mirror_type: "srv", signature_type: "fingerprints", fingerprints: "/usr/share/keys/pkg", enabled: yes } .... And finally run this command to update from the new (latest) repository metadata. [source,shell] .... # pkg update -f .... [[pkgng-pkg-info]] === Obtaining Information About Installed Packages Information about the packages installed on a system can be viewed by running `pkg info` which, when run without any switches, will list the package version for either all installed packages or the specified package. For example, to see which version of pkg is installed, run: [source,shell] .... # pkg info pkg pkg-1.1.4_1 .... [[pkgng-installing-deinstalling]] === Installing and Removing Packages To install a binary package use the following command, where _packagename_ is the name of the package to install: [source,shell] .... # pkg install packagename .... This command uses repository data to determine which version of the software to install and if it has any uninstalled dependencies. For example, to install curl: [source,shell] .... # pkg install curl Updating repository catalogue /usr/local/tmp/All/curl-7.31.0_1.txz 100% of 1181 kB 1380 kBps 00m01s /usr/local/tmp/All/ca_root_nss-3.15.1_1.txz 100% of 288 kB 1700 kBps 00m00s Updating repository catalogue The following 2 packages will be installed: Installing ca_root_nss: 3.15.1_1 Installing curl: 7.31.0_1 The installation will require 3 MB more space 0 B to be downloaded Proceed with installing packages [y/N]: y Checking integrity... done [1/2] Installing ca_root_nss-3.15.1_1... done [2/2] Installing curl-7.31.0_1... done Cleaning up cache files...Done .... The new package and any additional packages that were installed as dependencies can be seen in the installed packages list: [source,shell] .... # pkg info ca_root_nss-3.15.1_1 The root certificate bundle from the Mozilla Project curl-7.31.0_1 Non-interactive tool to get files from FTP, GOPHER, HTTP(S) servers pkg-1.1.4_6 New generation package manager .... Packages that are no longer needed can be removed with `pkg delete`. For example: [source,shell] .... # pkg delete curl The following packages will be deleted: curl-7.31.0_1 The deletion will free 3 MB Proceed with deleting packages [y/N]: y [1/1] Deleting curl-7.31.0_1... done .... [[pkgng-upgrading]] === Upgrading Installed Packages Installed packages can be upgraded to their latest versions by running: [source,shell] .... # pkg upgrade .... This command will compare the installed versions with those available in the repository catalogue and upgrade them from the repository. [[pkgng-auditing]] === Auditing Installed Packages Software vulnerabilities are regularly discovered in third-party applications. To address this, pkg includes a built-in auditing mechanism. To determine if there are any known vulnerabilities for the software installed on the system, run: [source,shell] .... # pkg audit -F .... [[pkgng-autoremove]] === Automatically Removing Unused Packages Removing a package may leave behind dependencies which are no longer required. Unneeded packages that were installed as dependencies (leaf packages) can be automatically detected and removed using: [source,shell] .... # pkg autoremove Packages to be autoremoved: ca_root_nss-3.15.1_1 The autoremoval will free 723 kB Proceed with autoremoval of packages [y/N]: y Deinstalling ca_root_nss-3.15.1_1... done .... Packages installed as dependencies are called _automatic_ packages. Non-automatic packages, i.e the packages that were explicity installed not as a dependency to another package, can be listed using: [source,shell] .... # pkg prime-list nginx openvpn sudo .... `pkg prime-list` is an alias command declared in [.filename]#/usr/local/etc/pkg.conf#. There are many others that can be used to query the package database of the system. For instance, command `pkg prime-origins` can be used to get the origin port directory of the list mentioned above: [source,shell] .... # pkg prime-origins www/nginx security/openvpn security/sudo .... This list can be used to rebuild all packages installed on a system using build tools such as package:ports-mgmt/poudriere[] or package:ports-mgmt/synth[]. Marking an installed package as automatic can be done using: [source,shell] .... # pkg set -A 1 devel/cmake .... Once a package is a leaf package and is marked as automatic, it gets selected by `pkg autoremove`. Marking an installed package as _not_ automatic can be done using: [source,shell] .... # pkg set -A 0 devel/cmake .... [[pkgng-backup]] === Restoring the Package Database Unlike the traditional package management system, pkg includes its own package database backup mechanism. This functionality is enabled by default. [TIP] ==== To disable the periodic script from backing up the package database, set `daily_backup_pkgdb_enable="NO"` in man:periodic.conf[5]. ==== To restore the contents of a previous package database backup, run the following command replacing _/path/to/pkg.sql_ with the location of the backup: [source,shell] .... # pkg backup -r /path/to/pkg.sql .... [NOTE] ==== If restoring a backup taken by the periodic script, it must be decompressed prior to being restored. ==== To run a manual backup of the pkg database, run the following command, replacing _/path/to/pkg.sql_ with a suitable file name and location: [source,shell] .... # pkg backup -d /path/to/pkg.sql .... [[pkgng-clean]] === Removing Stale Packages By default, pkg stores binary packages in a cache directory defined by `PKG_CACHEDIR` in man:pkg.conf[5]. Only copies of the latest installed packages are kept. Older versions of pkg kept all previous packages. To remove these outdated binary packages, run: [source,shell] .... # pkg clean .... The entire cache may be cleared by running: [source,shell] .... # pkg clean -a .... [[pkgng-set]] === Modifying Package Metadata Software within the FreeBSD Ports Collection can undergo major version number changes. To address this, pkg has a built-in command to update package origins. This can be useful, for example, if package:lang/php5[] is renamed to package:lang/php53[] so that package:lang/php5[] can now represent version `5.4`. To change the package origin for the above example, run: [source,shell] .... # pkg set -o lang/php5:lang/php53 .... As another example, to update package:lang/ruby18[] to package:lang/ruby19[], run: [source,shell] .... # pkg set -o lang/ruby18:lang/ruby19 .... As a final example, to change the origin of the [.filename]#libglut# shared libraries from package:graphics/libglut[] to package:graphics/freeglut[], run: [source,shell] .... # pkg set -o graphics/libglut:graphics/freeglut .... [NOTE] ==== When changing package origins, it is important to reinstall packages that are dependent on the package with the modified origin. To force a reinstallation of dependent packages, run: [source,shell] .... # pkg install -Rf graphics/freeglut .... ==== [[ports-using]] == Using the Ports Collection The Ports Collection is a set of [.filename]##Makefile##s, patches, and description files. Each set of these files is used to compile and install an individual application on FreeBSD, and is called a _port_. By default, the Ports Collection itself is stored as a subdirectory of [.filename]#/usr/ports#. [WARNING] ==== Before installing and using the Ports Collection, please be aware that it is generally ill-advised to use the Ports Collection in conjunction with the binary packages provided via pkg to install software. pkg, by default, tracks quarterly branch-releases of the ports tree and not HEAD. Dependencies could be different for a port in HEAD compared to its counterpart in a quarterly branch release and this could result in conflicts between dependencies installed by pkg and those from the Ports Collection. If the Ports Collection and pkg must be used in conjunction, then be sure that your Ports Collection and pkg are on the same branch release of the ports tree. ==== The Ports Collection contains directories for software categories. Inside each category are subdirectories for individual applications. Each application subdirectory contains a set of files that tells FreeBSD how to compile and install that program, called a _ports skeleton_. Each port skeleton includes these files and directories: * [.filename]#Makefile#: contains statements that specify how the application should be compiled and where its components should be installed. * [.filename]#distinfo#: contains the names and checksums of the files that must be downloaded to build the port. * [.filename]#files/#: this directory contains any patches needed for the program to compile and install on FreeBSD. This directory may also contain other files used to build the port. * [.filename]#pkg-descr#: provides a more detailed description of the program. * [.filename]#pkg-plist#: a list of all the files that will be installed by the port. It also tells the ports system which files to remove upon deinstallation. Some ports include [.filename]#pkg-message# or other files to handle special situations. For more details on these files, and on ports in general, refer to the link:{porters-handbook}[FreeBSD Porter's Handbook]. The port does not include the actual source code, also known as a [.filename]#distfile#. The extract portion of building a port will automatically save the downloaded source to [.filename]#/usr/ports/distfiles#. [[ports-using-installation-methods]] === Installing the Ports Collection Before an application can be compiled using a port, the Ports Collection must first be installed. If it was not installed during the installation of FreeBSD, use one of the following methods to install it: [[ports-using-portsnap-method]] [.procedure] **** *Procedure: Portsnap Method* The base system of FreeBSD includes Portsnap. This is a fast and user-friendly tool for retrieving the Ports Collection and is the recommended choice for most users not running FreeBSD-CURRENT. This utility connects to a FreeBSD site, verifies the secure key, and downloads a new copy of the Ports Collection. The key is used to verify the integrity of all downloaded files. . To download a compressed snapshot of the Ports Collection into [.filename]#/var/db/portsnap#: + [source,shell] .... # portsnap fetch .... + . When running Portsnap for the first time, extract the snapshot into [.filename]#/usr/ports#: + [source,shell] .... # portsnap extract .... + . After the first use of Portsnap has been completed as shown above, [.filename]#/usr/ports# can be updated as needed by running: + [source,shell] .... # portsnap fetch # portsnap update .... + When using `fetch`, the `extract` or the `update` operation may be run consecutively, like so: + [source,shell] .... # portsnap fetch update .... **** [[ports-using-git-method]] [.procedure] **** *Procedure: Git Method* If more control over the ports tree is needed or if local changes need to be maintained, or if running FreeBSD-CURRENT, Git can be used to obtain the Ports Collection. Refer to link:{committers-guide}#git-primer[the Git Primer] for a detailed description of Git. . Git must be installed before it can be used to check out the ports tree. If a copy of the ports tree is already present, install Git like this: + [source,shell] .... # cd /usr/ports/devel/git # make install clean .... + If the ports tree is not available, or pkg is being used to manage packages, Git can be installed as a package: + [source,shell] .... # pkg install git .... + . Check out a copy of the HEAD branch of the ports tree: + [source,shell] .... # git clone https://git.FreeBSD.org/ports.git /usr/ports .... + . Or, check out a copy of a quarterly branch: + [source,shell] .... # git clone https://git.FreeBSD.org/ports.git -b 2020Q3 /usr/ports .... + . As needed, update [.filename]#/usr/ports# after the initial Git checkout: + [source,shell] .... # git -C /usr/ports pull .... + . As needed, switch [.filename]#/usr/ports# to a different quarterly branch: + [source,shell] .... # git -C /usr/ports switch 2020Q4 .... **** === Installing Ports This section provides basic instructions on using the Ports Collection to install or remove software. The detailed description of available `make` targets and environment variables is available in man:ports[7]. [WARNING] ==== Before compiling any port, be sure to update the Ports Collection as described in the previous section. Since the installation of any third-party software can introduce security vulnerabilities, it is recommended to first check https://vuxml.freebsd.org/[] for known security issues related to the port. Alternately, run `pkg audit -F` before installing a new port. This command can be configured to automatically perform a security audit and an update of the vulnerability database during the daily security system check. For more information, refer to man:pkg-audit[8] and man:periodic[8]. ==== Using the Ports Collection assumes a working Internet connection. It also requires superuser privilege. To compile and install the port, change to the directory of the port to be installed, then type `make install` at the prompt. Messages will indicate the progress: [source,shell] .... # cd /usr/ports/sysutils/lsof # make install >> lsof_4.88D.freebsd.tar.gz doesn't seem to exist in /usr/ports/distfiles/. >> Attempting to fetch from ftp://lsof.itap.purdue.edu/pub/tools/unix/lsof/. ===> Extracting for lsof-4.88 ... [extraction output snipped] ... >> Checksum OK for lsof_4.88D.freebsd.tar.gz. ===> Patching for lsof-4.88.d,8 ===> Applying FreeBSD patches for lsof-4.88.d,8 ===> Configuring for lsof-4.88.d,8 ... [configure output snipped] ... ===> Building for lsof-4.88.d,8 ... [compilation output snipped] ... ===> Installing for lsof-4.88.d,8 ... [installation output snipped] ... ===> Generating temporary packing list ===> Compressing manual pages for lsof-4.88.d,8 ===> Registering installation for lsof-4.88.d,8 ===> SECURITY NOTE: This port has installed the following binaries which execute with increased privileges. /usr/local/sbin/lsof # .... Since `lsof` is a program that runs with increased privileges, a security warning is displayed as it is installed. Once the installation is complete, the prompt will be returned. Some shells keep a cache of the commands that are available in the directories listed in the `PATH` environment variable, to speed up lookup operations for the executable file of these commands. Users of the `tcsh` shell should type `rehash` so that a newly installed command can be used without specifying its full path. Use `hash -r` instead for the `sh` shell. Refer to the documentation for the shell for more information. During installation, a working subdirectory is created which contains all the temporary files used during compilation. Removing this directory saves disk space and minimizes the chance of problems later when upgrading to the newer version of the port: [source,shell] .... # make clean ===> Cleaning for lsof-88.d,8 # .... [NOTE] ==== To save this extra step, instead use `make install clean` when compiling the port. ==== ==== Customizing Ports Installation Some ports provide build options which can be used to enable or disable application components, provide security options, or allow for other customizations. Examples include package:www/firefox[], package:security/gpgme[], and package:mail/sylpheed-claws[]. If the port depends upon other ports which have configurable options, it may pause several times for user interaction as the default behavior is to prompt the user to select options from a menu. To avoid this and do all of the configuration in one batch, run `make config-recursive` within the port skeleton. Then, run `make install [clean]` to compile and install the port. [TIP] ==== When using `config-recursive`, the list of ports to configure are gathered by the `all-depends-list` target. It is recommended to run `make config-recursive` until all dependent ports options have been defined, and ports options screens no longer appear, to be certain that all dependency options have been configured. ==== There are several ways to revisit a port's build options menu in order to add, remove, or change these options after a port has been built. One method is to `cd` into the directory containing the port and type `make config`. Another option is to use `make showconfig`. Another option is to execute `make rmconfig` which will remove all selected options and allow you to start over. All of these options, and others, are explained in great detail in man:ports[7]. The ports system uses man:fetch[1] to download the source files, which supports various environment variables. The `FTP_PASSIVE_MODE`, `FTP_PROXY`, and `FTP_PASSWORD` variables may need to be set if the FreeBSD system is behind a firewall or FTP/HTTP proxy. See man:fetch[3] for the complete list of supported variables. For users who cannot be connected to the Internet all the time, `make fetch` can be run within [.filename]#/usr/ports#, to fetch all distfiles, or within a category, such as [.filename]#/usr/ports/net#, or within the specific port skeleton. Note that if a port has any dependencies, running this command in a category or ports skeleton will _not_ fetch the distfiles of ports from another category. Instead, use `make fetch-recursive` to also fetch the distfiles for all the dependencies of a port. In rare cases, such as when an organization has a local distfiles repository, the `MASTER_SITES` variable can be used to override the download locations specified in the [.filename]#Makefile#. When using, specify the alternate location: [source,shell] .... # cd /usr/ports/directory # make MASTER_SITE_OVERRIDE= \ ftp://ftp.organization.org/pub/FreeBSD/ports/distfiles/ fetch .... The `WRKDIRPREFIX` and `PREFIX` variables can override the default working and target directories. For example: [source,shell] .... # make WRKDIRPREFIX=/usr/home/example/ports install .... will compile the port in [.filename]#/usr/home/example/ports# and install everything under [.filename]#/usr/local#. [source,shell] .... # make PREFIX=/usr/home/example/local install .... will compile the port in [.filename]#/usr/ports# and install it in [.filename]#/usr/home/example/local#. And: [source,shell] .... # make WRKDIRPREFIX=../ports PREFIX=../local install .... will combine the two. These can also be set as environmental variables. Refer to the manual page for your shell for instructions on how to set an environmental variable. [[ports-removing]] === Removing Installed Ports Installed ports can be uninstalled using `pkg delete`. Examples for using this command can be found in the man:pkg-delete[8] manual page. Alternately, `make deinstall` can be run in the port's directory: [source,shell] .... # cd /usr/ports/sysutils/lsof # make deinstall ===> Deinstalling for sysutils/lsof ===> Deinstalling Deinstallation has been requested for the following 1 packages: lsof-4.88.d,8 The deinstallation will free 229 kB [1/1] Deleting lsof-4.88.d,8... done .... It is recommended to read the messages as the port is uninstalled. If the port has any applications that depend upon it, this information will be displayed but the uninstallation will proceed. In such cases, it may be better to reinstall the application in order to prevent broken dependencies. [[ports-upgrading]] === Upgrading Ports Over time, newer versions of software become available in the Ports Collection. This section describes how to determine which software can be upgraded and how to perform the upgrade. To determine if newer versions of installed ports are available, ensure that the latest version of the ports tree is installed, using the updating command described in either <> or <>. On FreeBSD 10 and later, or if the system has been converted to pkg, the following command will list the installed ports which are out of date: [source,shell] .... # pkg version -l "<" .... For FreeBSD 9._X_ and lower, the following command will list the installed ports that are out of date: [source,shell] .... # pkg_version -l "<" .... [IMPORTANT] ==== Before attempting an upgrade, read [.filename]#/usr/ports/UPDATING# from the top of the file to the date closest to the last time ports were upgraded or the system was installed. This file describes various issues and additional steps users may encounter and need to perform when updating a port, including such things as file format changes, changes in locations of configuration files, or any incompatibilities with previous versions. Make note of any instructions which match any of the ports that need upgrading and follow these instructions when performing the upgrade. ==== [[ports-upgrading-tools]] ==== Tools to Upgrade and Manage Ports The Ports Collection contains several utilities to perform the actual upgrade. Each has its strengths and weaknesses. Historically, most installations used either Portmaster or Portupgrade. Synth is a newer alternative. [NOTE] ==== The choice of which tool is best for a particular system is up to the system administrator. It is recommended practice to back up your data before using any of these tools. ==== [[portmaster]] ==== Upgrading Ports Using Portmaster package:ports-mgmt/portmaster[] is a very small utility for upgrading installed ports. It is designed to use the tools installed with the FreeBSD base system without depending on other ports or databases. To install this utility as a port: [source,shell] .... # cd /usr/ports/ports-mgmt/portmaster # make install clean .... Portmaster defines four categories of ports: * Root port: has no dependencies and is not a dependency of any other ports. * Trunk port: has no dependencies, but other ports depend upon it. * Branch port: has dependencies and other ports depend upon it. * Leaf port: has dependencies but no other ports depend upon it. To list these categories and search for updates: [source,shell] .... # portmaster -L ===>>> Root ports (No dependencies, not depended on) ===>>> ispell-3.2.06_18 ===>>> screen-4.0.3 ===>>> New version available: screen-4.0.3_1 ===>>> tcpflow-0.21_1 ===>>> 7 root ports ... ===>>> Branch ports (Have dependencies, are depended on) ===>>> apache22-2.2.3 ===>>> New version available: apache22-2.2.8 ... ===>>> Leaf ports (Have dependencies, not depended on) ===>>> automake-1.9.6_2 ===>>> bash-3.1.17 ===>>> New version available: bash-3.2.33 ... ===>>> 32 leaf ports ===>>> 137 total installed ports ===>>> 83 have new versions available .... This command is used to upgrade all outdated ports: [source,shell] .... # portmaster -a .... [NOTE] ==== By default, Portmaster makes a backup package before deleting the existing port. If the installation of the new version is successful, Portmaster deletes the backup. Using `-b` instructs Portmaster not to automatically delete the backup. Adding `-i` starts Portmaster in interactive mode, prompting for confirmation before upgrading each port. Many other options are available. Read through the manual page for man:portmaster[8] for details regarding their usage. ==== If errors are encountered during the upgrade process, add `-f` to upgrade and rebuild all ports: [source,shell] .... # portmaster -af .... Portmaster can also be used to install new ports on the system, upgrading all dependencies before building and installing the new port. To use this function, specify the location of the port in the Ports Collection: [source,shell] .... # portmaster shells/bash .... More information about package:ports-mgmt/portmaster[] may be found in its [.filename]#pkg-descr#. [[portupgrade]] ==== Upgrading Ports Using Portupgrade package:ports-mgmt/portupgrade[] is another utility that can be used to upgrade ports. It installs a suite of applications which can be used to manage ports. However, it is dependent upon Ruby. To install the port: [source,shell] .... # cd /usr/ports/ports-mgmt/portupgrade # make install clean .... Before performing an upgrade using this utility, it is recommended to scan the list of installed ports using `pkgdb -F` and to fix all the inconsistencies it reports. To upgrade all the outdated ports installed on the system, use `portupgrade -a`. Alternately, include `-i` to be asked for confirmation of every individual upgrade: [source,shell] .... # portupgrade -ai .... To upgrade only a specified application instead of all available ports, use `portupgrade _pkgname_`. It is very important to include `-R` to first upgrade all the ports required by the given application: [source,shell] .... # portupgrade -R firefox .... If `-P` is included, Portupgrade searches for available packages in the local directories listed in `PKG_PATH`. If none are available locally, it then fetches packages from a remote site. If packages can not be found locally or fetched remotely, Portupgrade will use ports. To avoid using ports entirely, specify `-PP`. This last set of options tells Portupgrade to abort if no packages are available: [source,shell] .... # portupgrade -PP gnome3 .... To just fetch the port distfiles, or packages, if `-P` is specified, without building or installing anything, use `-F`. For further information on all of the available switches, refer to the manual page for `portupgrade`. More information about package:ports-mgmt/portupgrade[] may be found in its [.filename]#pkg-descr#. [[ports-disk-space]] === Ports and Disk Space Using the Ports Collection will use up disk space over time. After building and installing a port, running `make clean` within the ports skeleton will clean up the temporary [.filename]#work# directory. If Portmaster is used to install a port, it will automatically remove this directory unless `-K` is specified. If Portupgrade is installed, this command will remove all [.filename]#work# directories found within the local copy of the Ports Collection: [source,shell] .... # portsclean -C .... In addition, outdated source distribution files accumulate in [.filename]#/usr/ports/distfiles# over time. To use Portupgrade to delete all the distfiles that are no longer referenced by any ports: [source,shell] .... # portsclean -D .... Portupgrade can remove all distfiles not referenced by any port currently installed on the system: [source,shell] .... # portsclean -DD .... If Portmaster is installed, use: [source,shell] .... # portmaster --clean-distfiles .... By default, this command is interactive and prompts the user to confirm if a distfile should be deleted. In addition to these commands, package:ports-mgmt/pkg_cutleaves[] automates the task of removing installed ports that are no longer needed. [[ports-poudriere]] == Building Packages with Poudriere Poudriere is a `BSD`-licensed utility for creating and testing FreeBSD packages. It uses FreeBSD jails to set up isolated compilation environments. These jails can be used to build packages for versions of FreeBSD that are different from the system on which it is installed, and also to build packages for i386 if the host is an amd64 system. Once the packages are built, they are in a layout identical to the official mirrors. These packages are usable by man:pkg[8] and other package management tools. Poudriere is installed using the package:ports-mgmt/poudriere[] package or port. The installation includes a sample configuration file [.filename]#/usr/local/etc/poudriere.conf.sample#. Copy this file to [.filename]#/usr/local/etc/poudriere.conf#. Edit the copied file to suit the local configuration. While `ZFS` is not required on the system running poudriere, it is beneficial. When `ZFS` is used, `ZPOOL` must be specified in [.filename]#/usr/local/etc/poudriere.conf# and `FREEBSD_HOST` should be set to a nearby mirror. Defining `CCACHE_DIR` enables the use of package:devel/ccache[] to cache compilation and reduce build times for frequently-compiled code. It may be convenient to put poudriere datasets in an isolated tree mounted at [.filename]#/poudriere#. Defaults for the other configuration values are adequate. The number of processor cores detected is used to define how many builds will run in parallel. Supply enough virtual memory, either with `RAM` or swap space. If virtual memory runs out, the compilation jails will stop and be torn down, resulting in weird error messages. [[poudriere-initialization]] === Initialize Jails and Port Trees After configuration, initialize poudriere so that it installs a jail with the required FreeBSD tree and a ports tree. Specify a name for the jail using `-j` and the FreeBSD version with `-v`. On systems running FreeBSD/amd64, the architecture can be set with `-a` to either `i386` or `amd64`. The default is the architecture shown by `uname`. [source,shell] .... # poudriere jail -c -j 11amd64 -v 11.4-RELEASE [00:00:00] Creating 11amd64 fs at /poudriere/jails/11amd64... done [00:00:00] Using pre-distributed MANIFEST for FreeBSD 11.4-RELEASE amd64 [00:00:00] Fetching base for FreeBSD 11.4-RELEASE amd64 /poudriere/jails/11amd64/fromftp/base.txz 125 MB 4110 kBps 31s [00:00:33] Extracting base... done [00:00:54] Fetching src for FreeBSD 11.4-RELEASE amd64 /poudriere/jails/11amd64/fromftp/src.txz 154 MB 4178 kBps 38s [00:01:33] Extracting src... done [00:02:31] Fetching lib32 for FreeBSD 11.4-RELEASE amd64 /poudriere/jails/11amd64/fromftp/lib32.txz 24 MB 3969 kBps 06s [00:02:38] Extracting lib32... done [00:02:42] Cleaning up... done [00:02:42] Recording filesystem state for clean... done [00:02:42] Upgrading using ftp /etc/resolv.conf -> /poudriere/jails/11amd64/etc/resolv.conf Looking up update.FreeBSD.org mirrors... 3 mirrors found. Fetching public key from update4.freebsd.org... done. Fetching metadata signature for 11.4-RELEASE from update4.freebsd.org... done. Fetching metadata index... done. Fetching 2 metadata files... done. Inspecting system... done. Preparing to download files... done. Fetching 124 patches.....10....20....30....40....50....60....70....80....90....100....110....120.. done. Applying patches... done. Fetching 6 files... done. The following files will be added as part of updating to 11.4-RELEASE-p1: /usr/src/contrib/unbound/.github /usr/src/contrib/unbound/.github/FUNDING.yml /usr/src/contrib/unbound/contrib/drop2rpz /usr/src/contrib/unbound/contrib/unbound_portable.service.in /usr/src/contrib/unbound/services/rpz.c /usr/src/contrib/unbound/services/rpz.h /usr/src/lib/libc/tests/gen/spawnp_enoexec.sh The following files will be updated as part of updating to 11.4-RELEASE-p1: […] Installing updates...Scanning //usr/share/certs/blacklisted for certificates... Scanning //usr/share/certs/trusted for certificates... done. 11.4-RELEASE-p1 [00:04:06] Recording filesystem state for clean... done [00:04:07] Jail 11amd64 11.4-RELEASE-p1 amd64 is ready to be used .... [source,shell] .... # poudriere ports -c -p local -m git+https [00:00:00] Creating local fs at /poudriere/ports/local... done [00:00:00] Checking out the ports tree... done .... On a single computer, poudriere can build ports with multiple configurations, in multiple jails, and from different port trees. Custom configurations for these combinations are called _sets_. See the CUSTOMIZATION section of man:poudriere[8] for details after package:ports-mgmt/poudriere[] or package:ports-mgmt/poudriere-devel[] is installed. The basic configuration shown here puts a single jail-, port-, and set-specific [.filename]#make.conf# in [.filename]#/usr/local/etc/poudriere.d#. The filename in this example is created by combining the jail name, port name, and set name: [.filename]#11amd64-local-workstation-make.conf#. The system [.filename]#make.conf# and this new file are combined at build time to create the [.filename]#make.conf# used by the build jail. Packages to be built are entered in [.filename]#11amd64-local-workstation-pkglist#: [.programlisting] .... editors/emacs devel/git ports-mgmt/pkg ... .... Options and dependencies for the specified ports are configured: [source,shell] .... # poudriere options -j 11amd64 -p local -z workstation -f 11amd64-local-workstation-pkglist .... Finally, packages are built and a package repository is created: [source,shell] .... # poudriere bulk -j 11amd64 -p local -z workstation -f 11amd64-local-workstation-pkglist .... While running, pressing kbd:[Ctrl+t] displays the current state of the build. Poudriere also builds files in [.filename]#/poudriere/logs/bulk/jailname# that can be used with a web server to display build information. After completion, the new packages are now available for installation from the poudriere repository. For more information on using poudriere, see man:poudriere[8] and the main web site, https://github.com/freebsd/poudriere/wiki[]. === Configuring pkg Clients to Use a Poudriere Repository While it is possible to use both a custom repository along side of the official repository, sometimes it is useful to disable the official repository. This is done by creating a configuration file that overrides and disables the official configuration file. Create [.filename]#/usr/local/etc/pkg/repos/FreeBSD.conf# that contains the following: [.programlisting] .... FreeBSD: { enabled: no } .... Usually it is easiest to serve a poudriere repository to the client machines via HTTP. Set up a webserver to serve up the package directory, for instance: [.filename]#/usr/local/poudriere/data/packages/11amd64#, where [.filename]#11amd64# is the name of the build. If the URL to the package repository is: `http://pkg.example.com/11amd64`, then the repository configuration file in [.filename]#/usr/local/etc/pkg/repos/custom.conf# would look like: [.programlisting] .... custom: { url: "http://pkg.example.com/11amd64", enabled: yes, } .... [[ports-nextsteps]] == Post-Installation Considerations Regardless of whether the software was installed from a binary package or port, most third-party applications require some level of configuration after installation. The following commands and locations can be used to help determine what was installed with the application. * Most applications install at least one default configuration file in [.filename]#/usr/local/etc#. In cases where an application has a large number of configuration files, a subdirectory will be created to hold them. Often, sample configuration files are installed which end with a suffix such as [.filename]#.sample#. The configuration files should be reviewed and possibly edited to meet the system's needs. To edit a sample file, first copy it without the [.filename]#.sample# extension. -* Applications which provide documentation will install it into [.filename]#/usr/local/shared/doc# and many applications also install manual pages. This documentation should be consulted before continuing. +* Applications which provide documentation will install it into [.filename]#/usr/local/share/doc# and many applications also install manual pages. This documentation should be consulted before continuing. * Some applications run services which must be added to [.filename]#/etc/rc.conf# before starting the application. These applications usually install a startup script in [.filename]#/usr/local/etc/rc.d#. See crossref:config[configtuning-starting-services,Starting Services] for more information. + [NOTE] ==== By design, applications do not run their startup script upon installation, nor do they run their stop script upon deinstallation or upgrade. This decision is left to the individual system administrator. ==== * Users of man:csh[1] should run `rehash` to rebuild the known binary list in the shells `PATH`. * Use `pkg info` to determine which files, man pages, and binaries were installed with the application. [[ports-broken]] == Dealing with Broken Ports When a port does not build or install, try the following: . Search to see if there is a fix pending for the port in the link:https://www.FreeBSD.org/support/[Problem Report database]. If so, implementing the proposed fix may fix the issue. . Ask the maintainer of the port for help. Type `make maintainer` in the ports skeleton or read the port's [.filename]#Makefile# to find the maintainer's email address. Remember to include the `$FreeBSD:` line from the port's [.filename]#Makefile# and the output leading up to the error in the email to the maintainer. + [NOTE] ==== Some ports are not maintained by an individual but instead by a group maintainer represented by a link:{mailing-list-faq}[mailing list]. Many, but not all, of these addresses look like mailto:freebsd-listname@FreeBSD.org[freebsd-listname@FreeBSD.org]. Please take this into account when sending an email. In particular, ports maintained by mailto:ports@FreeBSD.org[ports@FreeBSD.org] are not maintained by a specific individual. Instead, any fixes and support come from the general community who subscribe to that mailing list. More volunteers are always needed! ==== + If there is no response to the email, use Bugzilla to submit a bug report using the instructions in link:{problem-reports}[Writing FreeBSD Problem Reports]. . Fix it! The link:{porters-handbook}[Porter's Handbook] includes detailed information on the ports infrastructure so that you can fix the occasional broken port or even submit your own! . Install the package instead of the port using the instructions in <>. diff --git a/documentation/content/en/books/handbook/x11/_index.adoc b/documentation/content/en/books/handbook/x11/_index.adoc index b02e476fd4..5ffede7d23 100644 --- a/documentation/content/en/books/handbook/x11/_index.adoc +++ b/documentation/content/en/books/handbook/x11/_index.adoc @@ -1,1429 +1,1429 @@ --- title: Chapter 5. The X Window System part: Part I. Getting Started prev: books/handbook/ports next: books/handbook/partii description: This chapter describes how to install and configure Xorg on FreeBSD, which provides the open source X Window System used to provide a graphical environment tags: ["X11", "Xorg", "TrueType", "DE", "KDE", "Plasma", "Xfce", "Gnome", "XDM", "SDDM", "GDM", "KMS", "Intel", "AMD", "NVIDIA", "Anti-Aliased"] --- [[x11]] = The X Window System :doctype: book :toc: macro :toclevels: 1 :icons: font :sectnums: :sectnumlevels: 6 :source-highlighter: rouge :experimental: :skip-front-matter: :xrefstyle: basic :relfileprefix: ../ :outfilesuffix: :sectnumoffset: 5 ifeval::["{backend}" == "html5"] :imagesdir: ../../../../images/books/handbook/x11/ endif::[] ifeval::["{backend}" == "pdf"] :imagesdir: ../../../../static/images/books/handbook/x11/ endif::[] ifeval::["{backend}" == "epub3"] :imagesdir: ../../../../static/images/books/handbook/x11/ endif::[] include::shared/authors.adoc[] include::shared/releases.adoc[] include::shared/en/mailing-lists.adoc[] include::shared/en/teams.adoc[] include::shared/en/urls.adoc[] toc::[] [[x11-synopsis]] == Synopsis An installation of FreeBSD using bsdinstall does not automatically install a graphical user interface. This chapter describes how to install and configure Xorg, which provides the open source X Window System used to provide a graphical environment. It then describes how to find and install a desktop environment or window manager. [NOTE] ==== Users who prefer an installation method that automatically configures the Xorg should refer to https://ghostbsd.org[GhostBSD], https://www.midnightbsd.org[MidnightBSD] or https://www.nomad.org[NomadBSD]. ==== For more information on the video hardware that Xorg supports, refer to the http://www.x.org/[x.org] website. After reading this chapter, you will know: * The various components of the X Window System, and how they interoperate. * How to install and configure Xorg. * How to install and configure several window managers and desktop environments. * How to use TrueType(R) fonts in Xorg. * How to set up your system for graphical logins (XDM). Before reading this chapter, you should: * Know how to install additional third-party software as described in crossref:ports[ports,Installing Applications: Packages and Ports]. [[x-understanding]] == Terminology While it is not necessary to understand all of the details of the various components in the X Window System and how they interact, some basic knowledge of these components can be useful. X server:: X was designed from the beginning to be network-centric, and adopts a "client-server" model. In this model, the "X server" runs on the computer that has the keyboard, monitor, and mouse attached. The server's responsibility includes tasks such as managing the display, handling input from the keyboard and mouse, and handling input or output from other devices such as a tablet or a video projector. This confuses some people, because the X terminology is exactly backward to what they expect. They expect the "X server" to be the big powerful machine down the hall, and the "X client" to be the machine on their desk. X client:: Each X application, such as XTerm or Firefox, is a "client". A client sends messages to the server such as "Please draw a window at these coordinates", and the server sends back messages such as "The user just clicked on the OK button". + In a home or small office environment, the X server and the X clients commonly run on the same computer. It is also possible to run the X server on a less powerful computer and to run the X applications on a more powerful system. In this scenario, the communication between the X client and server takes place over the network. window manager:: X does not dictate what windows should look like on-screen, how to move them around with the mouse, which keystrokes should be used to move between windows, what the title bars on each window should look like, whether or not they have close buttons on them, and so on. Instead, X delegates this responsibility to a separate window manager application. There are http://www.xwinman.org/[dozens of window managers] available. Each window manager provides a different look and feel: some support virtual desktops, some allow customized keystrokes to manage the desktop, some have a "Start" button, and some are themeable, allowing a complete change of the desktop's look-and-feel. Window managers are available in the [.filename]#x11-wm# category of the Ports Collection. + Each window manager uses a different configuration mechanism. Some expect configuration file written by hand while others provide graphical tools for most configuration tasks. desktop environment:: KDE and GNOME are considered to be desktop environments as they include an entire suite of applications for performing common desktop tasks. These may include office suites, web browsers, and games. focus policy:: The window manager is responsible for the mouse focus policy. This policy provides some means for choosing which window is actively receiving keystrokes and it should also visibly indicate which window is currently active. + One focus policy is called "click-to-focus". In this model, a window becomes active upon receiving a mouse click. In the "focus-follows-mouse" policy, the window that is under the mouse pointer has focus and the focus is changed by pointing at another window. If the mouse is over the root window, then this window is focused. In the "sloppy-focus" model, if the mouse is moved over the root window, the most recently used window still has the focus. With sloppy-focus, focus is only changed when the cursor enters a new window, and not when exiting the current window. In the "click-to-focus" policy, the active window is selected by mouse click. The window may then be raised and appear in front of all other windows. All keystrokes will now be directed to this window, even if the cursor is moved to another window. + Different window managers support different focus models. All of them support click-to-focus, and the majority of them also support other policies. Consult the documentation for the window manager to determine which focus models are available. widgets:: Widget is a term for all of the items in the user interface that can be clicked or manipulated in some way. This includes buttons, check boxes, radio buttons, icons, and lists. A widget toolkit is a set of widgets used to create graphical applications. There are several popular widget toolkits, including Qt, used by KDE, and GTK+, used by GNOME. As a result, applications will have a different look and feel, depending upon which widget toolkit was used to create the application. [[x-install]] == Installing Xorg On FreeBSD, Xorg can be installed as a package or port. The binary package can be installed quickly but with fewer options for customization: [source,shell] .... # pkg install xorg .... To build and install from the Ports Collection: [source,shell] .... # cd /usr/ports/x11/xorg # make install clean .... Either of these installations results in the complete Xorg system being installed. Binary packages are the best option for most users. A smaller version of the X system suitable for experienced users is available in package:x11/xorg-minimal[]. Most of the documents, libraries, and applications will not be installed. Some applications require these additional components to function. [[x-config]] == Xorg Configuration [[x-config-quick-start]] === Quick Start Xorg supports most common video cards, keyboards, and pointing devices. [TIP] ==== Video cards, monitors, and input devices are automatically detected and do not require any manual configuration. Do not create [.filename]#xorg.conf# or run a `-configure` step unless automatic configuration fails. ==== [.procedure] . If Xorg has been used on this computer before, move or remove any existing configuration files: + [source,shell] .... # mv /etc/X11/xorg.conf ~/xorg.conf.etc # mv /usr/local/etc/X11/xorg.conf ~/xorg.conf.localetc .... . Add the user who will run Xorg to the `video` or `wheel` group to enable 3D acceleration when available. To add user _jru_ to whichever group is available: + [source,shell] .... # pw groupmod video -m jru || pw groupmod wheel -m jru .... . The `TWM` window manager is included by default. It is started when Xorg starts: + [source,shell] .... % startx .... . On some older versions of FreeBSD, the system console must be set to man:vt[4] before switching back to the text console will work properly. See <>. [[x-config-user-group]] === User Group for Accelerated Video Access to [.filename]#/dev/dri# is needed to allow 3D acceleration on video cards. It is usually simplest to add the user who will be running X to either the `video` or `wheel` group. Here, man:pw[8] is used to add user _slurms_ to the `video` group, or to the `wheel` group if there is no `video` group: [source,shell] .... # pw groupmod video -m slurms || pw groupmod wheel -m slurms .... [[x-config-kms]] === Kernel Mode Setting (`KMS`) When the computer switches from displaying the console to a higher screen resolution for X, it must set the video output _mode_. Recent versions of `Xorg` use a system inside the kernel to do these mode changes more efficiently. Older versions of FreeBSD use man:sc[4], which is not aware of the `KMS` system. The end result is that after closing X, the system console is blank, even though it is still working. The newer man:vt[4] console avoids this problem. Add this line to [.filename]#/boot/loader.conf# to enable man:vt[4]: [.programlisting] .... kern.vty=vt .... [[x-config-files]] === Configuration Files Manual configuration is usually not necessary. Please do not manually create configuration files unless autoconfiguration does not work. [[x-config-files-directory]] ==== Directory Xorg looks in several directories for configuration files. [.filename]#/usr/local/etc/X11/# is the recommended directory for these files on FreeBSD. Using this directory helps keep application files separate from operating system files. Storing configuration files in the legacy [.filename]#/etc/X11/# still works. However, this mixes application files with the base FreeBSD files and is not recommended. [[x-config-files-single-or-multi]] ==== Single or Multiple Files It is easier to use multiple files that each configure a specific setting than the traditional single [.filename]#xorg.conf#. These files are stored in the [.filename]#xorg.conf.d/# subdirectory of the main configuration file directory. The full path is typically [.filename]#/usr/local/etc/X11/xorg.conf.d/#. Examples of these files are shown later in this section. The traditional single [.filename]#xorg.conf# still works, but is neither as clear nor as flexible as multiple files in the [.filename]#xorg.conf.d/# subdirectory. [[x-config-video-cards]] === Video Cards The Ports framework provides the drm graphics drivers necessary for X11 operation on recent hardware. Users can use one of the following drivers available from package:graphics/drm-kmod[]. These drivers use interfaces in the kernel that are normally private. As such, it is strongly recommended that the drivers be built via the ports system via the `PORTS_MODULES` variable. With `PORTS_MODULES`, every time you build the kernel, the corresponding port(s) containing kernel modules are re-built against the updated sources. This ensures the kernel module stays in-sync with the kernel itself. The kernel and ports trees should be updated together for maximum compatibility. You can add `PORTS_MODULES` to your [.filename]#/etc/make.conf# file to ensure all kernels you build rebuild this module. Advanced users can add it to their kernel config files with the `makeoptions` directive. If you run GENERIC and use freebsd-update, you can just build the [.filename]#graphics/drm-kmod# or [.filename]#x11/nvidia-driver# port after each `freebsd-update install` invocation. [example] ==== [.filename]#/etc/make.conf# [.programlisting] .... SYSDIR=path/to/src/sys PORTS_MODULES=graphics/drm-kmod x11/nvidia-driver .... This will rebuild everything, but can select one or the other depending on which GPU / graphics card you have. ==== [[x-config-video-cards-ports]] Intel KMS driver, Radeon KMS driver, AMD KMS driver:: 2D and 3D acceleration is supported on most Intel KMS driver graphics cards provided by Intel. + Driver name: `i915kms` + 2D and 3D acceleration is supported on most older Radeon KMS driver graphics cards provided by AMD. + Driver name: `radeonkms` + 2D and 3D acceleration is supported on most newer AMD KMS driver graphics cards provided by AMD. + Driver name: `amdgpu` + For reference, please see https://en.wikipedia.org/wiki/List_of_Intel_graphics_processing_units[] or https://en.wikipedia.org/wiki/List_of_AMD_graphics_processing_units[] for a list of supported GPUs. [[x-config-video-cards-intel]] Intel(R):: 3D acceleration is supported on most Intel(R) graphics up to Ivy Bridge (HD Graphics 2500, 4000, and P4000), including Iron Lake (HD Graphics) and Sandy Bridge (HD Graphics 2000). + Driver name: `intel` + For reference, see https://en.wikipedia.org/wiki/List_of_Intel_graphics_processing_units[]. [[x-config-video-cards-radeon]] AMD(R) Radeon:: 2D and 3D acceleration is supported on Radeon cards up to and including the HD6000 series. + Driver name: `radeon` + For reference, see https://en.wikipedia.org/wiki/List_of_AMD_graphics_processing_units[]. [[x-config-video-cards-nvidia]] NVIDIA:: Several NVIDIA drivers are available in the [.filename]#x11# category of the Ports Collection. Install the driver that matches the video card. + For reference, see https://en.wikipedia.org/wiki/List_of_Nvidia_graphics_processing_units[]. + Kernel support for NVIDIA cards is found in either the [.filename]#x11/nvidia-driver# port or the [.filename]#x11/nvidia-driver-xxx# port. Modern cards use the former. Legacy cards use the -xxx ports, where xxx is one of 304, 340 or 390 indicating the version of the driver. For those, fill in the `-xxx` using the http://download.nvidia.com/XFree86/FreeBSD-x86_64/465.19.01/README/[ Supported NVIDIA GPU Products ] page. This page lists the devices supported by different versions of the driver. Legacy drivers run on both i386 and amd64. The current driver only supports amd64. Read http://download.nvidia.com/XFree86/FreeBSD-x86_64/465.19.01/README/[installation and configuration of NVIDIA driver] for details. While we recommend this driver be rebuilt with each kernel rebuild for maximum safety, it uses almost no private kernel interfaces and is usually safe across kernel updates. [[x-config-video-cards-hybrid]] Hybrid Combination Graphics:: Some notebook computers add additional graphics processing units to those built into the chipset or processor. _Optimus_ combines Intel(R) and NVIDIA hardware. _Switchable Graphics_ or _Hybrid Graphics_ are a combination of an Intel(R) or AMD(R) processor and an AMD(R) Radeon `GPU`. + Implementations of these hybrid graphics systems vary, and Xorg on FreeBSD is not able to drive all versions of them. + Some computers provide a `BIOS` option to disable one of the graphics adapters or select a _discrete_ mode which can be used with one of the standard video card drivers. For example, it is sometimes possible to disable the NVIDIA `GPU` in an Optimus system. The Intel(R) video can then be used with an Intel(R) driver. + `BIOS` settings depend on the model of computer. In some situations, both ``GPU``s can be left enabled, but creating a configuration file that only uses the main `GPU` in the `Device` section is enough to make such a system functional. [[x-config-video-cards-other]] Other Video Cards:: Drivers for some less-common video cards can be found in the [.filename]#x11-drivers# directory of the Ports Collection. + Cards that are not supported by a specific driver might still be usable with the package:x11-drivers/xf86-video-vesa[] driver. This driver is installed by package:x11/xorg[]. It can also be installed manually as package:x11-drivers/xf86-video-vesa[]. Xorg attempts to use this driver when a specific driver is not found for the video card. + package:x11-drivers/xf86-video-scfb[] is a similar nonspecialized video driver that works on many `UEFI` and ARM(R) computers. [[x-config-video-cards-file]] Setting the Video Driver in a File:: To set the Intel(R) driver in a configuration file: + [[x-config-video-cards-file-intel]] .Select Intel(R) Video Driver in a File [example] ==== [.filename]#/usr/local/etc/X11/xorg.conf.d/driver-intel.conf# [.programlisting] .... Section "Device" Identifier "Card0" Driver "intel" # BusID "PCI:1:0:0" EndSection .... If more than one video card is present, the `BusID` identifier can be uncommented and set to select the desired card. A list of video card bus ``ID``s can be displayed with `pciconf -lv | grep -B3 display`. ==== + To set the Radeon driver in a configuration file: + [[x-config-video-cards-file-radeon]] .Select Radeon Video Driver in a File [example] ==== [.filename]#/usr/local/etc/X11/xorg.conf.d/driver-radeon.conf# [.programlisting] .... Section "Device" Identifier "Card0" Driver "radeon" EndSection .... ==== + To set the `VESA` driver in a configuration file: + [[x-config-video-cards-file-vesa]] .Select `VESA` Video Driver in a File [example] ==== [.filename]#/usr/local/etc/X11/xorg.conf.d/driver-vesa.conf# [.programlisting] .... Section "Device" Identifier "Card0" Driver "vesa" EndSection .... ==== + To set the `scfb` driver for use with a `UEFI` or ARM(R) computer: + [[x-config-video-cards-file-scfb]] .Select `scfb` Video Driver in a File [example] ==== [.filename]#/usr/local/etc/X11/xorg.conf.d/driver-scfb.conf# [.programlisting] .... Section "Device" Identifier "Card0" Driver "scfb" EndSection .... ==== [[x-config-monitors]] === Monitors Almost all monitors support the Extended Display Identification Data standard (`EDID`). Xorg uses `EDID` to communicate with the monitor and detect the supported resolutions and refresh rates. Then it selects the most appropriate combination of settings to use with that monitor. Other resolutions supported by the monitor can be chosen by setting the desired resolution in configuration files, or after the X server has been started with man:xrandr[1]. [[x-config-monitors-xrandr]] Using man:xrandr[1]:: Run man:xrandr[1] without any parameters to see a list of video outputs and detected monitor modes: + [source,shell] .... % xrandr Screen 0: minimum 320 x 200, current 3000 x 1920, maximum 8192 x 8192 DVI-0 connected primary 1920x1200+1080+0 (normal left inverted right x axis y axis) 495mm x 310mm 1920x1200 59.95*+ 1600x1200 60.00 1280x1024 85.02 75.02 60.02 1280x960 60.00 1152x864 75.00 1024x768 85.00 75.08 70.07 60.00 832x624 74.55 800x600 75.00 60.32 640x480 75.00 60.00 720x400 70.08 DisplayPort-0 disconnected (normal left inverted right x axis y axis) HDMI-0 disconnected (normal left inverted right x axis y axis) .... + This shows that the `DVI-0` output is being used to display a screen resolution of 1920x1200 pixels at a refresh rate of about 60 Hz. Monitors are not attached to the `DisplayPort-0` and `HDMI-0` connectors. + Any of the other display modes can be selected with man:xrandr[1]. For example, to switch to 1280x1024 at 60 Hz: + [source,shell] .... % xrandr --output DVI-0 --mode 1280x1024 --rate 60 .... + A common task is using the external video output on a notebook computer for a video projector. + The type and quantity of output connectors varies between devices, and the name given to each output varies from driver to driver. What one driver calls `HDMI-1`, another might call `HDMI1`. So the first step is to run man:xrandr[1] to list all the available outputs: + [source,shell] .... % xrandr Screen 0: minimum 320 x 200, current 1366 x 768, maximum 8192 x 8192 LVDS1 connected 1366x768+0+0 (normal left inverted right x axis y axis) 344mm x 193mm 1366x768 60.04*+ 1024x768 60.00 800x600 60.32 56.25 640x480 59.94 VGA1 connected (normal left inverted right x axis y axis) 1280x1024 60.02 + 75.02 1280x960 60.00 1152x864 75.00 1024x768 75.08 70.07 60.00 832x624 74.55 800x600 72.19 75.00 60.32 56.25 640x480 75.00 72.81 66.67 60.00 720x400 70.08 HDMI1 disconnected (normal left inverted right x axis y axis) DP1 disconnected (normal left inverted right x axis y axis) .... + Four outputs were found: the built-in panel `LVDS1`, and external `VGA1`, `HDMI1`, and `DP1` connectors. + The projector has been connected to the `VGA1` output. man:xrandr[1] is now used to set that output to the native resolution of the projector and add the additional space to the right side of the desktop: + [source,shell] .... % xrandr --output VGA1 --auto --right-of LVDS1 .... + `--auto` chooses the resolution and refresh rate detected by `EDID`. If the resolution is not correctly detected, a fixed value can be given with `--mode` instead of the `--auto` statement. For example, most projectors can be used with a 1024x768 resolution, which is set with `--mode 1024x768`. + man:xrandr[1] is often run from [.filename]#.xinitrc# to set the appropriate mode when X starts. [[x-config-monitors-files]] Setting Monitor Resolution in a File:: To set a screen resolution of 1024x768 in a configuration file: + .Set Screen Resolution in a File [example] ==== [.filename]#/usr/local/etc/X11/xorg.conf.d/screen-resolution.conf# [.programlisting] .... Section "Screen" Identifier "Screen0" Device "Card0" SubSection "Display" Modes "1024x768" EndSubSection EndSection .... ==== + The few monitors that do not have `EDID` can be configured by setting `HorizSync` and `VertRefresh` to the range of frequencies supported by the monitor. + .Manually Setting Monitor Frequencies [example] ==== [.filename]#/usr/local/etc/X11/xorg.conf.d/monitor0-freq.conf# [.programlisting] .... Section "Monitor" Identifier "Monitor0" HorizSync 30-83 # kHz VertRefresh 50-76 # Hz EndSection .... ==== [[x-config-input]] === Input Devices [[x-config-input-keyboard]] ==== Keyboards [[x-config-input-keyboard-layout]] Keyboard Layout:: The standardized location of keys on a keyboard is called a _layout_. Layouts and other adjustable parameters are listed in man:xkeyboard-config[7]. + A United States layout is the default. To select an alternate layout, set the `XkbLayout` and `XkbVariant` options in an `InputClass`. This will be applied to all input devices that match the class. + This example selects a French keyboard layout. + .Setting a Keyboard Layout [example] ==== [.filename]#/usr/local/etc/X11/xorg.conf.d/keyboard-fr.conf# [.programlisting] .... Section "InputClass" Identifier "KeyboardDefaults" MatchIsKeyboard "on" Option "XkbLayout" "fr" EndSection .... ==== + .Setting Multiple Keyboard Layouts [example] ==== Set United States, Spanish, and Ukrainian keyboard layouts. Cycle through these layouts by pressing kbd:[Alt+Shift]. package:x11/xxkb[] or package:x11/sbxkb[] can be used for improved layout switching control and current layout indicators. [.filename]#/usr/local/etc/X11/xorg.conf.d/kbd-layout-multi.conf# [.programlisting] .... Section "InputClass" Identifier "All Keyboards" MatchIsKeyboard "yes" Option "XkbLayout" "us, es, ua" EndSection .... ==== [[x-config-input-keyboard-zap]] Closing Xorg From the Keyboard:: X can be closed with a combination of keys. By default, that key combination is not set because it conflicts with keyboard commands for some applications. Enabling this option requires changes to the keyboard `InputDevice` section: + .Enabling Keyboard Exit from X [example] ==== [.filename]#/usr/local/etc/X11/xorg.conf.d/keyboard-zap.conf# [.programlisting] .... Section "InputClass" Identifier "KeyboardDefaults" MatchIsKeyboard "on" Option "XkbOptions" "terminate:ctrl_alt_bksp" EndSection .... ==== [[x11-input-mice]] ==== Mice and Pointing Devices [IMPORTANT] ==== If using package:xorg-server[] 1.20.8 or later under FreeBSD {rel121-current} and not using man:moused[8], add `kern.evdev.rcpt_mask=12` to [.filename]#/etc/sysctl.conf#. ==== Many mouse parameters can be adjusted with configuration options. See man:mousedrv[4] for a full list. [[x11-input-mice-buttons]] Mouse Buttons:: The number of buttons on a mouse can be set in the mouse `InputDevice` section of [.filename]#xorg.conf#. To set the number of buttons to 7: + .Setting the Number of Mouse Buttons [example] ==== [.filename]#/usr/local/etc/X11/xorg.conf.d/mouse0-buttons.conf# [.programlisting] .... Section "InputDevice" Identifier "Mouse0" Option "Buttons" "7" EndSection .... ==== [[x-config-manual-configuration]] === Manual Configuration In some cases, Xorg autoconfiguration does not work with particular hardware, or a different configuration is desired. For these cases, a custom configuration file can be created. [WARNING] ==== Do not create manual configuration files unless required. Unnecessary manual configuration can prevent proper operation. ==== A configuration file can be generated by Xorg based on the detected hardware. This file is often a useful starting point for custom configurations. Generating an [.filename]#xorg.conf#: [source,shell] .... # Xorg -configure .... The configuration file is saved to [.filename]#/root/xorg.conf.new#. Make any changes desired, then test that file (using `-retro` so there is a visible background) with: [source,shell] .... # Xorg -retro -config /root/xorg.conf.new .... After the new configuration has been adjusted and tested, it can be split into smaller files in the normal location, [.filename]#/usr/local/etc/X11/xorg.conf.d/#. [[x-fonts]] == Using Fonts in Xorg [[type1]] === Type1 Fonts The default fonts that ship with Xorg are less than ideal for typical desktop publishing applications. Large presentation fonts show up jagged and unprofessional looking, and small fonts are almost completely unintelligible. However, there are several free, high quality Type1 (PostScript(R)) fonts available which can be readily used with Xorg. For instance, the URW font collection (package:x11-fonts/urwfonts[]) includes high quality versions of standard type1 fonts (Times Roman(TM), Helvetica(TM), Palatino(TM) and others). The Freefonts collection (package:x11-fonts/freefonts[]) includes many more fonts, but most of them are intended for use in graphics software such as the Gimp, and are not complete enough to serve as screen fonts. In addition, Xorg can be configured to use TrueType(R) fonts with a minimum of effort. For more details on this, see the man:X[7] manual page or <>. To install the above Type1 font collections from binary packages, run the following commands: [source,shell] .... # pkg install urwfonts .... Alternatively, to build from the Ports Collection, run the following commands: [source,shell] .... # cd /usr/ports/x11-fonts/urwfonts # make install clean .... And likewise with the freefont or other collections. To have the X server detect these fonts, add an appropriate line to the X server configuration file ([.filename]#/etc/X11/xorg.conf#), which reads: [.programlisting] .... -FontPath "/usr/local/shared/fonts/urwfonts/" +FontPath "/usr/local/share/fonts/urwfonts/" .... Alternatively, at the command line in the X session run: [source,shell] .... -% xset fp+ /usr/local/shared/fonts/urwfonts +% xset fp+ /usr/local/share/fonts/urwfonts % xset fp rehash .... This will work but will be lost when the X session is closed, unless it is added to the startup file ([.filename]#~/.xinitrc# for a normal `startx` session, or [.filename]#~/.xsession# when logging in through a graphical login manager like XDM). A third way is to use the new [.filename]#/usr/local/etc/fonts/local.conf# as demonstrated in <>. [[truetype]] === TrueType(R) Fonts Xorg has built in support for rendering TrueType(R) fonts. There are two different modules that can enable this functionality. The freetype module is used in this example because it is more consistent with the other font rendering back-ends. To enable the freetype module just add the following line to the `"Module"` section of [.filename]#/etc/X11/xorg.conf#. [.programlisting] .... Load "freetype" .... -Now make a directory for the TrueType(R) fonts (for example, [.filename]#/usr/local/shared/fonts/TrueType#) and copy all of the TrueType(R) fonts into this directory. Keep in mind that TrueType(R) fonts cannot be directly taken from an Apple(R) Mac(R); they must be in UNIX(R)/MS-DOS(R)/Windows(R) format for use by Xorg. Once the files have been copied into this directory, use mkfontscale to create a [.filename]#fonts.dir#, so that the X font renderer knows that these new files have been installed. `mkfontscale` can be installed as a package: +Now make a directory for the TrueType(R) fonts (for example, [.filename]#/usr/local/share/fonts/TrueType#) and copy all of the TrueType(R) fonts into this directory. Keep in mind that TrueType(R) fonts cannot be directly taken from an Apple(R) Mac(R); they must be in UNIX(R)/MS-DOS(R)/Windows(R) format for use by Xorg. Once the files have been copied into this directory, use mkfontscale to create a [.filename]#fonts.dir#, so that the X font renderer knows that these new files have been installed. `mkfontscale` can be installed as a package: [source,shell] .... # pkg install mkfontscale .... Then create an index of X font files in a directory: [source,shell] .... -# cd /usr/local/shared/fonts/TrueType +# cd /usr/local/share/fonts/TrueType # mkfontscale .... Now add the TrueType(R) directory to the font path. This is just the same as described in <>: [source,shell] .... -% xset fp+ /usr/local/shared/fonts/TrueType +% xset fp+ /usr/local/share/fonts/TrueType % xset fp rehash .... or add a `FontPath` line to [.filename]#xorg.conf#. Now Gimp, LibreOffice, and all of the other X applications should now recognize the installed TrueType(R) fonts. Extremely small fonts (as with text in a high resolution display on a web page) and extremely large fonts (within LibreOffice) will look much better now. [[antialias]] === Anti-Aliased Fonts -All fonts in Xorg that are found in [.filename]#/usr/local/shared/fonts/# and [.filename]#~/.fonts/# are automatically made available for anti-aliasing to Xft-aware applications. Most recent applications are Xft-aware, including KDE, GNOME, and Firefox. +All fonts in Xorg that are found in [.filename]#/usr/local/share/fonts/# and [.filename]#~/.fonts/# are automatically made available for anti-aliasing to Xft-aware applications. Most recent applications are Xft-aware, including KDE, GNOME, and Firefox. To control which fonts are anti-aliased, or to configure anti-aliasing properties, create (or edit, if it already exists) the file [.filename]#/usr/local/etc/fonts/local.conf#. Several advanced features of the Xft font system can be tuned using this file; this section describes only some simple possibilities. For more details, please see man:fonts-conf[5]. This file must be in XML format. Pay careful attention to case, and make sure all tags are properly closed. The file begins with the usual XML header followed by a DOCTYPE definition, and then the `` tag: [.programlisting] .... .... -As previously stated, all fonts in [.filename]#/usr/local/shared/fonts/# as well as [.filename]#~/.fonts/# are already made available to Xft-aware applications. To add another directory outside of these two directory trees, add a line like this to [.filename]#/usr/local/etc/fonts/local.conf#: +As previously stated, all fonts in [.filename]#/usr/local/share/fonts/# as well as [.filename]#~/.fonts/# are already made available to Xft-aware applications. To add another directory outside of these two directory trees, add a line like this to [.filename]#/usr/local/etc/fonts/local.conf#: [.programlisting] .... /path/to/my/fonts .... After adding new fonts, and especially new font directories, rebuild the font caches: [source,shell] .... # fc-cache -f .... Anti-aliasing makes borders slightly fuzzy, which makes very small text more readable and removes "staircases" from large text, but can cause eyestrain if applied to normal text. To exclude font sizes smaller than 14 point from anti-aliasing, include these lines: [.programlisting] .... 14 false 14 false .... Spacing for some monospaced fonts might also be inappropriate with anti-aliasing. This seems to be an issue with KDE, in particular. One possible fix is to force the spacing for such fonts to be 100. Add these lines: [.programlisting] .... fixed mono console mono .... (this aliases the other common names for fixed fonts as `"mono"`), and then add: [.programlisting] .... mono 100 .... Certain fonts, such as Helvetica, may have a problem when anti-aliased. Usually this manifests itself as a font that seems cut in half vertically. At worst, it may cause applications to crash. To avoid this, consider adding the following to [.filename]#local.conf#: [.programlisting] .... Helvetica sans-serif .... After editing [.filename]#local.conf#, make certain to end the file with the `` tag. Not doing this will cause changes to be ignored. Users can add personalized settings by creating their own [.filename]#~/.config/fontconfig/fonts.conf#. This file uses the same `XML` format described above. One last point: with an LCD screen, sub-pixel sampling may be desired. This basically treats the (horizontally separated) red, green and blue components separately to improve the horizontal resolution; the results can be dramatic. To enable this, add the line somewhere in [.filename]#local.conf#: [.programlisting] .... unknown rgb .... [NOTE] ==== Depending on the sort of display, `rgb` may need to be changed to `bgr`, `vrgb` or `vbgr`: experiment and see which works best. ==== [[x-xdm]] == The X Display Manager Xorg provides an X Display Manager, XDM, which can be used for login session management. XDM provides a graphical interface for choosing which display server to connect to and for entering authorization information such as a login and password combination. This section demonstrates how to configure the X Display Manager on FreeBSD. Some desktop environments provide their own graphical login manager. Refer to <> for instructions on how to configure the GNOME Display Manager and <> for instructions on how to configure the KDE Display Manager. === Configuring XDM To install XDM, use the package:x11/xdm[] package or port. Once installed, XDM can be configured to run when the machine boots up by adding the following line to [.filename]#/etc/rc.conf#: [.programlisting] .... xdm_enable="YES" .... XDM will run on the ninth virtual terminal by default. The XDM configuration directory is located in [.filename]#/usr/local/etc/X11/xdm#. This directory contains several files used to change the behavior and appearance of XDM, as well as a few scripts and programs used to set up the desktop when XDM is running. <> summarizes the function of each of these files. The exact syntax and usage of these files is described in man:xdm[1]. [[xdm-config-files]] .XDM Configuration Files [cols="1,1", frame="none", options="header"] |=== | File | Description |[.filename]#Xaccess# |The protocol for connecting to XDM is called the X Display Manager Connection Protocol (`XDMCP`). This file is a client authorization ruleset for controlling `XDMCP` connections from remote machines. By default, this file does not allow any remote clients to connect. |[.filename]#Xresources# |This file controls the look and feel of the XDM display chooser and login screens. The default configuration is a simple rectangular login window with the hostname of the machine displayed at the top in a large font and "Login:" and "Password:" prompts below. The format of this file is identical to the app-defaults file described in the Xorg documentation. |[.filename]#Xservers# |The list of local and remote displays the chooser should provide as login choices. |[.filename]#Xsession# |Default session script for logins which is run by XDM after a user has logged in. This points to a customized session script in [.filename]#~/.xsession#. |[.filename]#Xsetup_#* |Script to automatically launch applications before displaying the chooser or login interfaces. There is a script for each display being used, named [.filename]#Xsetup_*#, where `*` is the local display number. Typically these scripts run one or two programs in the background such as `xconsole`. |[.filename]#xdm-config# |Global configuration for all displays running on this machine. |[.filename]#xdm-errors# |Contains errors generated by the server program. If a display that XDM is trying to start hangs, look at this file for error messages. These messages are also written to the user's [.filename]#~/.xsession-errors# on a per-session basis. |[.filename]#xdm-pid# |The running process `ID` of XDM. |=== === Configuring Remote Access By default, only users on the same system can login using XDM. To enable users on other systems to connect to the display server, edit the access control rules and enable the connection listener. To configure XDM to listen for any remote connection, comment out the `DisplayManager.requestPort` line in [.filename]#/usr/local/etc/X11/xdm/xdm-config# by putting a `!` in front of it: [source,shell] .... ! SECURITY: do not listen for XDMCP or Chooser requests ! Comment out this line if you want to manage X terminals with xdm DisplayManager.requestPort: 0 .... Save the edits and restart XDM. To restrict remote access, look at the example entries in [.filename]#/usr/local/etc/X11/xdm/Xaccess# and refer to man:xdm[1] for further information. [[x11-wm]] == Desktop Environments This section describes how to install three popular desktop environments on a FreeBSD system. A desktop environment can range from a simple window manager to a complete suite of desktop applications. Over a hundred desktop environments are available in the [.filename]#x11-wm# category of the Ports Collection. [[x11-wm-gnome]] === GNOME GNOME is a user-friendly desktop environment. It includes a panel for starting applications and displaying status, a desktop, a set of tools and applications, and a set of conventions that make it easy for applications to cooperate and be consistent with each other. More information regarding GNOME on FreeBSD can be found at https://www.FreeBSD.org/gnome[https://www.FreeBSD.org/gnome]. That web site contains additional documentation about installing, configuring, and managing GNOME on FreeBSD. This desktop environment can be installed from a package: [source,shell] .... # pkg install gnome3 .... To instead build GNOME from ports, use the following command. GNOME is a large application and will take some time to compile, even on a fast computer. [source,shell] .... # cd /usr/ports/x11/gnome3 # make install clean .... GNOME requires [.filename]#/proc# to be mounted. Add this line to [.filename]#/etc/fstab# to mount this file system automatically during system startup: [.programlisting] .... proc /proc procfs rw 0 0 .... GNOME uses D-Bus for a message bus and hardware abstraction. These applications are automatically installed as dependencies of GNOME. Enable them in [.filename]#/etc/rc.conf# so they will be started when the system boots: [.programlisting] .... dbus_enable="YES" .... After installation, configure Xorg to start GNOME. The easiest way to do this is to enable the GNOME Display Manager, GDM, which is installed as part of the GNOME package or port. It can be enabled by adding this line to [.filename]#/etc/rc.conf#: [.programlisting] .... gdm_enable="YES" .... It is often desirable to also start all GNOME services. To achieve this, add a second line to [.filename]#/etc/rc.conf#: [.programlisting] .... gnome_enable="YES" .... GDM will start automatically when the system boots. A second method for starting GNOME is to type `startx` from the command-line after configuring [.filename]#~/.xinitrc#. If this file already exists, replace the line that starts the current window manager with one that starts [.filename]#/usr/local/bin/gnome-session#. If this file does not exist, create it with this command: [source,shell] .... % echo "exec /usr/local/bin/gnome-session" > ~/.xinitrc .... A third method is to use XDM as the display manager. In this case, create an executable [.filename]#~/.xsession#: [source,shell] .... % echo "exec /usr/local/bin/gnome-session" > ~/.xsession .... [[x11-wm-kde]] === KDE KDE is another easy-to-use desktop environment. This desktop provides a suite of applications with a consistent look and feel, a standardized menu and toolbars, keybindings, color-schemes, internationalization, and a centralized, dialog-driven desktop configuration. More information on KDE can be found at http://www.kde.org/[http://www.kde.org/]. For FreeBSD-specific information, consult http://freebsd.kde.org/[http://freebsd.kde.org]. To install the KDE package, type: [source,shell] .... # pkg install x11/kde5 .... To instead build the KDE port, use the following command. Installing the port will provide a menu for selecting which components to install. KDE is a large application and will take some time to compile, even on a fast computer. [source,shell] .... # cd /usr/ports/x11/kde5 # make install clean .... KDE requires [.filename]#/proc# to be mounted. Add this line to [.filename]#/etc/fstab# to mount this file system automatically during system startup: [.programlisting] .... proc /proc procfs rw 0 0 .... KDE uses D-Bus for a message bus and hardware abstraction. These applications are automatically installed as dependencies of KDE. Enable them in [.filename]#/etc/rc.conf# so they will be started when the system boots: [.programlisting] .... dbus_enable="YES" .... Since KDE Plasma 5, the KDE Display Manager, KDM is no longer developed. A possible replacement is SDDM. To install it, type: [source,shell] .... # pkg install x11/sddm .... Add this line to [.filename]#/etc/rc.conf#: [.programlisting] .... sddm_enable="YES" .... A second method for launching KDE Plasma is to type `startx` from the command line. For this to work, the following line is needed in [.filename]#~/.xinitrc#: [.programlisting] .... exec ck-launch-session startplasma-x11 .... A third method for starting KDE Plasma is through XDM. To do so, create an executable [.filename]#~/.xsession# as follows: [source,shell] .... % echo "exec ck-launch-session startplasma-x11" > ~/.xsession .... Once KDE Plasma is started, refer to its built-in help system for more information on how to use its various menus and applications. [[x11-wm-xfce]] === Xfce Xfce is a desktop environment based on the GTK+ toolkit used by GNOME. However, it is more lightweight and provides a simple, efficient, easy-to-use desktop. It is fully configurable, has a main panel with menus, applets, and application launchers, provides a file manager and sound manager, and is themeable. Since it is fast, light, and efficient, it is ideal for older or slower machines with memory limitations. More information on Xfce can be found at http://www.xfce.org/[http://www.xfce.org]. To install the Xfce package: [source,shell] .... # pkg install xfce .... Alternatively, to build the port: [source,shell] .... # cd /usr/ports/x11-wm/xfce4 # make install clean .... Xfce uses D-Bus for a message bus. This application is automatically installed as dependency of Xfce. Enable it in [.filename]#/etc/rc.conf# so it will be started when the system boots: [.programlisting] .... dbus_enable="YES" .... Unlike GNOME or KDE, Xfce does not provide its own login manager. In order to start Xfce from the command line by typing `startx`, first create [.filename]#~/.xinitrc# with this command: [source,shell] .... % echo ". /usr/local/etc/xdg/xfce4/xinitrc" > ~/.xinitrc .... An alternate method is to use XDM. To configure this method, create an executable [.filename]#~/.xsession#: [source,shell] .... % echo ". /usr/local/etc/xdg/xfce4/xinitrc" > ~/.xsession .... [[x-compiz-fusion]] == Installing Compiz Fusion One way to make using a desktop computer more pleasant is with nice 3D effects. Installing the Compiz Fusion package is easy, but configuring it requires a few steps that are not described in the port's documentation. [[x-compiz-video-card]] === Setting up the FreeBSD nVidia Driver Desktop effects can cause quite a load on the graphics card. For an nVidia-based graphics card, the proprietary driver is required for good performance. Users of other graphics cards can skip this section and continue with the [.filename]#xorg.conf# configuration. To determine which nVidia driver is needed see the link:{faq}#idp59950544[FAQ question on the subject]. Having determined the correct driver to use for your card, installation is as simple as installing any other package. For example, to install the latest driver: [source,shell] .... # pkg install x11/nvidia-driver .... The driver will create a kernel module, which needs to be loaded at system startup. Add the following line to [.filename]#/boot/loader.conf#: [.programlisting] .... nvidia_load="YES" .... [NOTE] ==== To immediately load the kernel module into the running kernel issue a command like `kldload nvidia`. However, it has been noted that some versions of Xorg will not function properly if the driver is not loaded at boot time. After editing [.filename]#/boot/loader.conf#, a reboot is recommended. ==== With the kernel module loaded, you normally only need to change a single line in [.filename]#xorg.conf# to enable the proprietary driver: Find the following line in [.filename]#/etc/X11/xorg.conf#: [.programlisting] .... Driver "nv" .... and change it to: [.programlisting] .... Driver "nvidia" .... Start the GUI as usual, and you should be greeted by the nVidia splash. Everything should work as usual. [[xorg-configuration]] === Configuring `xorg.conf` for Desktop Effects To enable Compiz Fusion, [.filename]#/etc/X11/xorg.conf# needs to be modified: Add the following section to enable composite effects: [.programlisting] .... Section "Extensions" Option "Composite" "Enable" EndSection .... Locate the "Screen" section which should look similar to the one below: [.programlisting] .... Section "Screen" Identifier "Screen0" Device "Card0" Monitor "Monitor0" ... .... and add the following two lines (after "Monitor" will do): [.programlisting] .... DefaultDepth 24 Option "AddARGBGLXVisuals" "True" .... Locate the "Subsection" that refers to the screen resolution that you wish to use. For example, if you wish to use 1280x1024, locate the section that follows. If the desired resolution does not appear in any subsection, you may add the relevant entry by hand: [.programlisting] .... SubSection "Display" Viewport 0 0 Modes "1280x1024" EndSubSection .... A color depth of 24 bits is needed for desktop composition, change the above subsection to: [.programlisting] .... SubSection "Display" Viewport 0 0 Depth 24 Modes "1280x1024" EndSubSection .... Finally, confirm that the "glx" and "extmod" modules are loaded in the "Module" section: [.programlisting] .... Section "Module" Load "extmod" Load "glx" ... .... The preceding can be done automatically with package:x11/nvidia-xconfig[] by running (as root): [source,shell] .... # nvidia-xconfig --add-argb-glx-visuals # nvidia-xconfig --composite # nvidia-xconfig --depth=24 .... [[compiz-fusion]] === Installing and Configuring Compiz Fusion Installing Compiz Fusion is as simple as any other package: [source,shell] .... # pkg install x11-wm/compiz-fusion .... When the installation is finished, start your graphic desktop and at a terminal, enter the following commands (as a normal user): [source,shell] .... % compiz --replace --sm-disable --ignore-desktop-hints ccp & % emerald --replace & .... Your screen will flicker for a few seconds, as your window manager (e.g., Metacity if you are using GNOME) is replaced by Compiz Fusion. Emerald takes care of the window decorations (i.e., close, minimize, maximize buttons, title bars and so on). You may convert this to a trivial script and have it run at startup automatically (e.g., by adding to "Sessions" in a GNOME desktop): [.programlisting] .... #! /bin/sh compiz --replace --sm-disable --ignore-desktop-hints ccp & emerald --replace & .... Save this in your home directory as, for example, [.filename]#start-compiz# and make it executable: [source,shell] .... % chmod +x ~/start-compiz .... Then use the GUI to add it to [.guimenuitem]#Startup Programs# (located in [.guimenuitem]#System#, [.guimenuitem]#Preferences#, [.guimenuitem]#Sessions# on a GNOME desktop). To actually select all the desired effects and their settings, execute (again as a normal user) the Compiz Config Settings Manager: [source,shell] .... % ccsm .... [NOTE] ==== In GNOME, this can also be found in the [.guimenuitem]#System#, [.guimenuitem]#Preferences# menu. ==== If you have selected "gconf support" during the build, you will also be able to view these settings using `gconf-editor` under `apps/compiz`. [[x11-troubleshooting]] == Troubleshooting If the mouse does not work, you will need to first configure it before proceeding. In recent Xorg versions, the `InputDevice` sections in [.filename]#xorg.conf# are ignored in favor of the autodetected devices. To restore the old behavior, add the following line to the `ServerLayout` or `ServerFlags` section of this file: [.programlisting] .... Option "AutoAddDevices" "false" .... Input devices may then be configured as in previous versions, along with any other options needed (e.g., keyboard layout switching). [NOTE] ==== As previously explained the hald daemon will, by default, automatically detect your keyboard. There are chances that your keyboard layout or model will not be correct, desktop environments like GNOME, KDE or Xfce provide tools to configure the keyboard. However, it is possible to set the keyboard properties directly either with the help of the man:setxkbmap[1] utility or with a hald's configuration rule. For example if, one wants to use a PC 102 keys keyboard coming with a french layout, we have to create a keyboard configuration file for hald called [.filename]#x11-input.fdi# and saved in the [.filename]#/usr/local/etc/hal/fdi/policy# directory. This file should contain the following lines: [.programlisting] .... pc102 fr .... If this file already exists, just copy and add to your file the lines regarding the keyboard configuration. You will have to reboot your machine to force hald to read this file. It is possible to do the same configuration from an X terminal or a script with this command line: [source,shell] .... % setxkbmap -model pc102 -layout fr .... -[.filename]#/usr/local/shared/X11/xkb/rules/base.lst# lists the various keyboard, layouts and options available. +[.filename]#/usr/local/share/X11/xkb/rules/base.lst# lists the various keyboard, layouts and options available. ==== The [.filename]#xorg.conf.new# configuration file may now be tuned to taste. Open the file in a text editor such as man:emacs[1] or man:ee[1]. If the monitor is an older or unusual model that does not support autodetection of sync frequencies, those settings can be added to [.filename]#xorg.conf.new# under the `"Monitor"` section: [.programlisting] .... Section "Monitor" Identifier "Monitor0" VendorName "Monitor Vendor" ModelName "Monitor Model" HorizSync 30-107 VertRefresh 48-120 EndSection .... Most monitors support sync frequency autodetection, making manual entry of these values unnecessary. For the few monitors that do not support autodetection, avoid potential damage by only entering values provided by the manufacturer. X allows DPMS (Energy Star) features to be used with capable monitors. The man:xset[1] program controls the time-outs and can force standby, suspend, or off modes. If you wish to enable DPMS features for your monitor, you must add the following line to the monitor section: [.programlisting] .... Option "DPMS" .... While the [.filename]#xorg.conf.new# configuration file is still open in an editor, select the default resolution and color depth desired. This is defined in the `"Screen"` section: [.programlisting] .... Section "Screen" Identifier "Screen0" Device "Card0" Monitor "Monitor0" DefaultDepth 24 SubSection "Display" Viewport 0 0 Depth 24 Modes "1024x768" EndSubSection EndSection .... The `DefaultDepth` keyword describes the color depth to run at by default. This can be overridden with the `-depth` command line switch to man:Xorg[1]. The `Modes` keyword describes the resolution to run at for the given color depth. Note that only VESA standard modes are supported as defined by the target system's graphics hardware. In the example above, the default color depth is twenty-four bits per pixel. At this color depth, the accepted resolution is 1024 by 768 pixels. Finally, write the configuration file and test it using the test mode given above. [NOTE] ==== One of the tools available to assist you during troubleshooting process are the Xorg log files, which contain information on each device that the Xorg server attaches to. Xorg log file names are in the format of [.filename]#/var/log/Xorg.0.log#. The exact name of the log can vary from [.filename]#Xorg.0.log# to [.filename]#Xorg.8.log# and so forth. ==== If all is well, the configuration file needs to be installed in a common location where man:Xorg[1] can find it. This is typically [.filename]#/etc/X11/xorg.conf# or [.filename]#/usr/local/etc/X11/xorg.conf#. [source,shell] .... # cp xorg.conf.new /etc/X11/xorg.conf .... The Xorg configuration process is now complete. Xorg may be now started with the man:startx[1] utility. The Xorg server may also be started with the use of man:xdm[1]. === Configuration with Intel(R) `i810` Graphics Chipsets Configuration with Intel(R) i810 integrated chipsets requires the [.filename]#agpgart# AGP programming interface for Xorg to drive the card. See the man:agp[4] driver manual page for more information. This will allow configuration of the hardware as any other graphics board. Note on systems without the man:agp[4] driver compiled in the kernel, trying to load the module with man:kldload[8] will not work. This driver has to be in the kernel at boot time through being compiled in or using [.filename]#/boot/loader.conf#. === Adding a Widescreen Flatpanel to the Mix This section assumes a bit of advanced configuration knowledge. If attempts to use the standard configuration tools above have not resulted in a working configuration, there is information enough in the log files to be of use in getting the setup working. Use of a text editor will be necessary. Current widescreen (WSXGA, WSXGA+, WUXGA, WXGA, WXGA+, et.al.) formats support 16:10 and 10:9 formats or aspect ratios that can be problematic. Examples of some common screen resolutions for 16:10 aspect ratios are: * 2560x1600 * 1920x1200 * 1680x1050 * 1440x900 * 1280x800 At some point, it will be as easy as adding one of these resolutions as a possible `Mode` in the `Section "Screen"` as such: [.programlisting] .... Section "Screen" Identifier "Screen0" Device "Card0" Monitor "Monitor0" DefaultDepth 24 SubSection "Display" Viewport 0 0 Depth 24 Modes "1680x1050" EndSubSection EndSection .... Xorg is smart enough to pull the resolution information from the widescreen via I2C/DDC information so it knows what the monitor can handle as far as frequencies and resolutions. If those `ModeLines` do not exist in the drivers, one might need to give Xorg a little hint. Using [.filename]#/var/log/Xorg.0.log# one can extract enough information to manually create a `ModeLine` that will work. Simply look for information resembling this: [.programlisting] .... (II) MGA(0): Supported additional Video Mode: (II) MGA(0): clock: 146.2 MHz Image Size: 433 x 271 mm (II) MGA(0): h_active: 1680 h_sync: 1784 h_sync_end 1960 h_blank_end 2240 h_border: 0 (II) MGA(0): v_active: 1050 v_sync: 1053 v_sync_end 1059 v_blanking: 1089 v_border: 0 (II) MGA(0): Ranges: V min: 48 V max: 85 Hz, H min: 30 H max: 94 kHz, PixClock max 170 MHz .... This information is called EDID information. Creating a `ModeLine` from this is just a matter of putting the numbers in the correct order: [.programlisting] .... ModeLine <4 horiz. timings> <4 vert. timings> .... So that the `ModeLine` in `Section "Monitor"` for this example would look like this: [.programlisting] .... Section "Monitor" Identifier "Monitor1" VendorName "Bigname" ModelName "BestModel" ModeLine "1680x1050" 146.2 1680 1784 1960 2240 1050 1053 1059 1089 Option "DPMS" EndSection .... Now having completed these simple editing steps, X should start on your new widescreen monitor. [[compiz-troubleshooting]] === Troubleshooting Compiz Fusion ==== I have installed Compiz Fusion, and after running the commands you mention, my windows are left without title bars and buttons. What is wrong? You are probably missing a setting in [.filename]#/etc/X11/xorg.conf#. Review this file carefully and check especially the `DefaultDepth` and `AddARGBGLXVisuals` directives. ==== When I run the command to start Compiz Fusion, the X server crashes and I am back at the console. What is wrong? If you check [.filename]#/var/log/Xorg.0.log#, you will probably find error messages during the X startup. The most common would be: [source,shell] .... (EE) NVIDIA(0): Failed to initialize the GLX module; please check in your X (EE) NVIDIA(0): log file that the GLX module has been loaded in your X (EE) NVIDIA(0): server, and that the module is the NVIDIA GLX module. If (EE) NVIDIA(0): you continue to encounter problems, Please try (EE) NVIDIA(0): reinstalling the NVIDIA driver. .... This is usually the case when you upgrade Xorg. You will need to reinstall the package:x11/nvidia-driver[] package so glx is built again.