aboutsummaryrefslogtreecommitdiff
path: root/contrib/top/Porting
diff options
context:
space:
mode:
Diffstat (limited to 'contrib/top/Porting')
-rw-r--r--contrib/top/Porting165
1 files changed, 165 insertions, 0 deletions
diff --git a/contrib/top/Porting b/contrib/top/Porting
new file mode 100644
index 000000000000..7fd3ff469d46
--- /dev/null
+++ b/contrib/top/Porting
@@ -0,0 +1,165 @@
+Instructions for porting top to other architectures.
+
+This is still a preliminary document. Suggestions for improvement are
+most welcome.
+
+My address is now "lefebvre@dis.anl.gov".
+
+Before you embark on a port, please send me a mail message telling me
+what platform you are porting top to. There are three reasons for
+this: (1) I may already have a port, (2) module naming needs to be
+centralized, (3) I want to loosely track the various porting efforts.
+You do not need to wait for an "okay", but I do want to know that you
+are working on it. And of course, once it is finished, please send me
+the module files so that I can add them to the main distribution!
+
+----------
+
+There is one set of functions which extract all the information that
+top needs for display. These functions are collected in to one file.
+To make top work on a different architecture simply requires a
+different implementation of these functions. The functions for a
+given architecture "foo" are stored in a file called "m_foo.c". The
+Configure script looks for these files and lets the configurer choose
+one of them. This file is called a "module". The idea is that making
+top work on a different machine only requires one additional file and
+does not require changes to any existing files.
+
+A module template is included in the distribution, called "m-template".
+To write your own module, it is a good idea to start with this template.
+If you architecture is similar to one for which a module already
+exists, then you can start with that module instead. If you do so,
+remember to change the "AUTHOR" section at the top!
+
+The first comment in a module contains information which is extracted
+and used by Configure. This information is marked with words in all
+capitals (such as "SYNOPSIS:" and "LIBS:"). Go look at m-template: it
+is fairly self-explanatory. The text after "LIBS:" (on the same line)
+is extracted and included in the LIBS definition of the Makefile so
+that extra libraries which may be necessary on some machines (such as
+"-lkvm") can be specified in the module. The text after "CFLAGS:"
+(on the same line) is extracted and included as flags in the "CFLAGS"
+definition of the Makefile (thus in every compilation step). This is
+used for rare circumstances only: please don't abuse this hook.
+
+Some operating systems have idiosyncrasies which will affect the form
+and/or content of the information top displays. You may wish to
+document such anomalies in the top man page. This can be done by adding
+a file called m_{modulename}.man (where {modulename} is replaced with
+the name of the module). Configure will automatically add this file to
+the end of the man page. See m_sunos4.man for an example.
+
+A module is concerned with two structures:
+
+The statics struct is filled in by machine_init. Each item is a
+pointer to a list of character pointers. The list is terminated
+with a null pointer.
+
+struct statics
+{
+ char **procstate_names; /* process state names */
+ char **cpustate_names; /* cpu state names */
+ char **memory_names; /* memory information names */
+};
+
+The system_info struct is filled in by get_system_info and
+get_process_info.
+
+struct system_info
+{
+ int last_pid; /* last pid assigned (0 means non-sequential assignment) */
+ double load_avg[NUM_AVERAGES]; /* see below */
+ int p_total; /* total number of processes */
+ int p_active; /* number of procs considered "active" */
+ int *procstates; /* array of process state counters */
+ int *cpustates; /* array of cpustate counters */
+ int *memory; /* memory information */
+};
+
+The last three pointers each point to an array of integers. The
+length of the array is determined by the length of the corresponding
+_names array in the statics structure. Furthermore, if an entry in a
+_names array is the empty string ("") then the corresponding value in
+the value array will be skipped over. The display routine displays,
+for example, the string procstate_names[0] then the number
+procstates[0], then procstate_names[1], procstates[1], etc. until
+procstate_names[N] == NULL. This allows for a tremendous amount of
+flexibility in labeling the displayed values.
+
+"procstates" and "memory" are displayed as straight integer values.
+Values in "cpustates" are displayed as a percentage * 10. For
+example, the (integer) value 105 is displayed as 10.5%.
+
+These routines must be defined by the machine dependent module.
+
+int machine_init(struct statics *)
+
+ returns 0 on success and -1 on failure,
+ prints error messages
+
+char *format_header(char *)
+
+ Returns a string which should be used as the header for the
+ process display area. The argument is a string used to label
+ the username column (either "USERNAME" or "UID") and is always
+ 8 characters in length.
+
+void get_system_info(struct system_info *)
+
+caddr_t get_process_info(struct system_info *, int, int, int (*func)())
+
+ returns a handle to use with format_next_process
+
+char *format_next_process(caddr_t, char *(*func)())
+
+ returns string which describes next process
+
+int proc_compare(caddr_t, caddr_t)
+
+ qsort comparison function
+
+uid_t proc_owner(pid_t)
+
+ Returns the uid owner of the process specified by the pid argument.
+ This function is VERY IMPORTANT. If it fails to do its job, then
+ top may pose a security risk.
+
+
+get_process_info is called immediately after get_system_info. In
+fact, the two functions could be rolled in to one. The reason they
+are not is mostly historical.
+
+Top relies on the existence of a function called "setpriority" to
+change a process's priority. This exists as a kernel call on most 4.3
+BSD derived Unixes. If neither your operating system nor your C
+library supplies such a function, then you will need to add one to the
+module. It is defined as follows:
+
+ int setpriority (int dummy, int who, int niceval)
+
+ For the purposes of top, the first argument is meaningless.
+ The second is the pid and the third is the new nice value.
+ This function should behave just like a kernel call, setting
+ errno and returning -1 in case of an error. This function MUST
+ check to make sure that a non-root user does not specify a nice
+ value less than the process's current value. If it detects such
+ a condition, it should set errno to EACCES and return -1.
+ Other possible ERRNO values: ESRCH when pid "who" does not exist,
+ EPERM when the invoker is not root and not the same as the
+ process owner.
+
+Note that top checks process ownership and should never call setpriority
+when the invoker's uid is not root and not the same as the process's owner
+uid.
+
+
+The file "machine.h" contains definitions which are useful to modules
+and to top.c (such as the structure definitions). You SHOULD NOT need
+to change it when porting to a new platform.
+
+Porting to a new platform should NOT require any changes to existing
+files. You should only need to add m_ files. If you feel you need a
+change in one of the existing files, please contact me so that we can
+discuss the details. I want to keep such changes as general as
+possible.
+