The security of your projects relies on the security of your CVS repository, the repository's computer and its environment, all the computers that contain sandboxes, your access method, your backup storage, and your developer's working environments. The security of access methods is covered in Chapter 8. General computer security is outside the scope of this book, but you should consider it when securing your repository.
Sandboxes are checked out of the repository with the username of the user who creates them or does the checking out. If the client's computer has a group that matches the group ownership of files in the repository, files in the sandbox are usually stored with that group ownership.
Permissions in a sandbox depend on the settings for new files in the sandbox computer's operating system, on whether the user has the CVSREAD environment variable set, and on whether the files are being watched with the cvs watch commands. If a file is imported or added as executable, it is set as executable in the repository and the executable setting is preserved in the sandboxes. The CVSREAD environment variable is described in Section 6.10, later in this chapter.
Repository security is more complex than sandbox security, and it is based on the filesystem security for the operating system that the repository is running under. The specific instructions in this section are based on traditional Unix and Linux filesystem permissions, but the principles can be used to secure a repository running under systems with more extensive security options, such as Access Control Lists (ACLs).
Secure the repository root directory so that only users who are allowed to create new projects have write access. Users who will be using existing repository projects, even though they may be creating and writing to project files, should have read access to this directory.
Securing the repository root directory usually involves creating a group for the users with the right to import projects, setting the repository root directory read-write-execute for the repository's owner and that group, and setting it read-execute for all others.
You may want to set the Set Group ID (SGID) bit on the repository root directory to ensure that all projects are imported with a reasonably secure group. In many cases, people who can import projects can also be trusted with the CVSROOT subdirectory. Example 6-1 shows a small repository and the permissions and groups set for it. The user cvs is the owner of the repository, and the group cvs is the group for people who can create new projects. The user doppel created the wowow project for the people in the group sauce, and the user jenn created the wizzard project for those in the group wizzard.
/var/lib/cvs$ ls -la drwxrwsr-x 39 cvs cvs 4096 Sep 17 22:52 . drwxrwsr-x 41 root staff 4096 Sep 17 23:07 .. drwxrwsr-x 4 cvs cvs 4096 Sep 17 23:30 CVSROOT drwxrwsr-x 4 doppel sauce 4096 Aug 17 12:08 wowow drwxrwsr-x 4 jenn wizzard 4096 Sep 24 20:14 wizzard
The permissions on the CVSROOT directory in the repository should be considered carefully. A user who can modify the files in this directory may be able to cause CVS to run arbitrary commands on the repository computer. Only trusted users should have write access to this directory or most of the files in this directory.
All users who will have access to CVS should have read access to all the files in the CVSROOT directory.
Two files should be writeable (as well as readable) to all users who will be running CVS commands: the history file and the val-tags file. If the history file exists, most CVS commands attempt to append to it, and fail if they can't. Many commands attempt to modify val-tags. Neither of these files trigger scripts; both are purely informational.
You have only directory-level control over the security of project files. CVS sets the permissions of files stored in the repository and overwrites any read or write permissions you set when it next changes the files.
When a file is changed, CVS writes a temporary version of the file, then copies the temporary file over the original file. The resulting file is owned by the person who last changed it.
Group ownership of project files and directories controls project security. Ensure that each project is group-owned by a group with appropriate membership, and set the group permissions for the project files to the project's group. Also set the SGID bit, as described earlier in Section 6.3.1.
Users who change the files in a project repository must have read, write, and execute access to the project directories. Because files are overwritten when changed (during the commit process), a user changing a file needs write permission to the directory the file is in, but not to the file itself. Usually, you create a group with the appropriate access and add your project members to that group.
Users reading project files must have read and execute access to the project directories and write access to the location of the project's locks, usually the project's directories. The LockDir option in the config file in the repository's CVSROOT directory can change the location of the lock files if you want to avoid giving out write permissions to the repository's project directories.
To ensure that group ownership is set correctly, ensure that your project directories automatically create the correct group permissions for new files. In Unix or Linux, set each directory's SGID bit to ensure that any new files or directories created in the directory are created with the same group ID as the directory they are created in. Use the command chmod g+s directory to set the SGID bit. The directories in Example 6-1 have their SGID bits set.
If a file is executable when it is imported or added, CVS sets it executable in the repository. The executable bit in the repository copy of the file is preserved when the file is checked out to the sandbox. If a file should be executable but isn't, or shouldn't be but is, change the setting in the repository with chmod.
When you change the settings on a file in the repository, the file permissions of existing files in existing sandboxes are unaffected. To correct the sandbox permissions, delete the file from the sandbox and then retrieve a new copy with cvs update.
Committing a file with sandbox permissions that differ from the repository permissions does not affect the permissions in the repository version. Repository files acquire sandbox file permissions only during an add.
If you need to set project file permissions differently from your usual file permissions, you can use the CVSUMASK environment variable, which specifies a umask setting for CVS to use. The CVS process on the repository server reads the calling user's CVSUMASK and, if this variable is present, uses the umask to set the permissions of any files or directories the CVS process creates. The format of CVSUMASK is the same as the Unix and Linux shell setting umask.
CVS normally uses the project's repository directories for lock files. Consider designating an alternate directory by using the LockDir setting in the config file in the repository's CVSROOT directory. This allows you to restrict users from writing to the project directories. If you use LockDir, remember to modify any scripts you are using to freeze the repository. Also, when you need to remove a lock manually, be sure to look in the LockDir directory. Changing the lock directory is rarely needed, but you should be aware that it is possible.