Fix: Patch for Parallel Tools 9.0.23350 to support Linux Kernel 3.12 (Ubuntu 14.04)

Discussion in 'Linux Guest OS Discussion' started by eugenesan, Nov 29, 2013.

  1. eugenesan

    eugenesan

    Messages:
    5
    Below is a patch to fix recent changes in uid/gid treatment for filesystems.
    Above also required changes in parameters parsing, so I replaced custom parameters parsing with Kernel's native routines.
    Not extensively tested but works fine for me.

    (I had to paste it here inline since Attachment upload is broken under Chrome and Firefox... which means TABs are not preserved)

    Usage:
    1) Mount Parallells Tools CD in virtual machine (Virtual Machine -> Install/Reinstall Parallels Tools)
    2) Make temporary copy of Parallels Tools, enter and patch it:
    $ cp -R /media/$USER/Parallels\ Tools /tmp/
    $ cd /tmp/Parallels\ Tools/kmods
    $ tar -xaf prl_mod.tar.gz
    $ patch -p1 -d prl_fs < parallels-tools-linux-3.12-prl-fs-9.0.23350.941886.patch
    $ tar -czf prl_mod.tar.gz prl_eth prl_fs prl_fs_freeze prl_tg Makefile.kmods dkms.conf
    3) Install normally:
    $ sudo /tmp/Parallels\ Tools/install
    4) If successfully installed, reboot

    Code:
    diff -Nru prl_fs.orig/SharedFolders/Guest/Linux/prl_fs/inode.c prl_fs/SharedFolders/Guest/Linux/prl_fs/inode.c
    --- prl_fs.orig/SharedFolders/Guest/Linux/prl_fs/inode.c	2013-11-11 17:56:58.000000000 +0200
    +++ prl_fs/SharedFolders/Guest/Linux/prl_fs/inode.c	2013-11-29 20:41:53.689167040 +0200
    @@ -199,10 +199,18 @@
     	if (attr->valid & _PATTR_MODE)
     		inode->i_mode = (inode->i_mode & S_IFMT) | (attr->mode & 0777);
     	if ((attr->valid & _PATTR_UID) &&
    -	    (sbi->plain || sbi->share || attr->uid == -1))
    +#if LINUX_VERSION_CODE >= KERNEL_VERSION(3,5,0)
    +	    (sbi->plain || sbi->share || __kuid_val(attr->uid) == -1))
    +#else
    +	    (sbi->plain || sbi->share || attr->uid == -1)))
    +#endif
     		inode->i_uid = attr->uid;
     	if ((attr->valid & _PATTR_GID) &&
    -	    (sbi->plain || sbi->share || attr->gid == -1))
    +#if LINUX_VERSION_CODE >= KERNEL_VERSION(3,5,0)
    +	    (sbi->plain || sbi->share || __kgid_val(attr->gid) == -1))
    +#else
    +	    (sbi->plain || sbi->share || attr->gid == -1)))
    +#endif
     		inode->i_gid = attr->gid;
     	return;
     }
    @@ -521,13 +529,21 @@
     
     	generic_fillattr(dentry->d_inode, stat);
     	if (PRLFS_SB(dentry->d_sb)->share) {
    +#if LINUX_VERSION_CODE >= KERNEL_VERSION(3,5,0)
    +		if (__kuid_val(stat->uid) != -1)
    +#else
     		if (stat->uid != -1)
    +#endif
     #if LINUX_VERSION_CODE < KERNEL_VERSION(2,6,29)
     			stat->uid = current->fsuid;
     #else
     			stat->uid = current->cred->fsuid;
     #endif
    +#if LINUX_VERSION_CODE >= KERNEL_VERSION(3,5,0)
    +		if (__kgid_val(stat->gid) != -1)
    +#else
     		if (stat->gid != -1)
    +#endif
     #if LINUX_VERSION_CODE < KERNEL_VERSION(2,6,29)
     			stat->gid = current->fsgid;
     #else
    @@ -577,9 +593,17 @@
     	mode = inode->i_mode;
     	isdir = S_ISDIR(mode);
     
    +#if LINUX_VERSION_CODE >= KERNEL_VERSION(3,5,0)
    +	if (__kuid_val(inode->i_uid) != -1)
    +#else
     	if (inode->i_uid != -1)
    +#endif
     		mode = mode >> 6;
    +#if LINUX_VERSION_CODE >= KERNEL_VERSION(3,5,0)
    +	else if (__kgid_val(inode->i_gid) != -1)
    +#else
     	else if (inode->i_gid != -1)
    +#endif
     		mode = mode >> 3;
     	mode &= 0007;
     	mask &= MAY_READ | MAY_WRITE | MAY_EXEC;
    diff -Nru prl_fs.orig/SharedFolders/Guest/Linux/prl_fs/prlfs.h prl_fs/SharedFolders/Guest/Linux/prl_fs/prlfs.h
    --- prl_fs.orig/SharedFolders/Guest/Linux/prl_fs/prlfs.h	2013-11-11 17:56:58.000000000 +0200
    +++ prl_fs/SharedFolders/Guest/Linux/prl_fs/prlfs.h	2013-11-29 20:46:27.662771996 +0200
    @@ -28,8 +28,13 @@
     	struct	pci_dev *pdev;
     	unsigned sfid;
     	unsigned ttl;
    +#if LINUX_VERSION_CODE >= KERNEL_VERSION(3,5,0)
    +	kuid_t uid;
    +	kgid_t gid;
    +#else
     	uid_t uid;
     	gid_t gid;
    +#endif
     	int readonly;
     	int share;
     	int plain;
    diff -Nru prl_fs.orig/SharedFolders/Guest/Linux/prl_fs/super.c prl_fs/SharedFolders/Guest/Linux/prl_fs/super.c
    --- prl_fs.orig/SharedFolders/Guest/Linux/prl_fs/super.c	2013-11-11 17:56:58.000000000 +0200
    +++ prl_fs/SharedFolders/Guest/Linux/prl_fs/super.c	2013-11-29 20:28:39.212000000 +0200
    @@ -13,6 +13,7 @@
     #include <linux/seq_file.h>
     #include <linux/ctype.h>
     #include <linux/vfs.h>
    +#include <linux/parser.h>
     #include "prlfs.h"
     #include "prlfs_compat.h"
     
    @@ -26,38 +27,35 @@
     extern struct file_operations prlfs_names_fops;
     extern struct inode_operations prlfs_names_iops;
     
    -static int prlfs_strtoui(char *cp, unsigned *result){
    -	int ret = 0;
    -	unsigned ui = 0;
    -	unsigned digit;
    -
    -	if (!cp || (*cp == 0))
    -		return -EINVAL;
    -
    -	while (*cp) {
    -		if (isdigit(*cp)) {
    -			digit = *cp - '0';
    -		} else {
    -			ret = -EINVAL;
    -			break;
    -		}
    -		if (ui > ui * 10U + digit)
    -			return -EINVAL;
    -		ui = ui * 10U + digit;
    -		cp++;
    -	}
    -
    -	if (ret == 0)
    -		*result = ui;
    -
    -	return ret;
    -}
    +enum {
    +	Opt_uid,
    +	Opt_gid,
    +	Opt_ttl,
    +	Opt_nls,
    +	Opt_share,
    +	Opt_plain,
    +	Opt_sf,
    +	Opt_err,
    +};
    +
    +static const match_table_t prlfs_tokens = {
    +	{Opt_uid, "uid=%d"},
    +	{Opt_gid, "gid=%d"},
    +	{Opt_ttl, "ttl=%u"},
    +	{Opt_nls, "nls=%s"},
    +	{Opt_share, "share"},
    +	{Opt_plain, "plain"},
    +	{Opt_sf, "sf=%s"},
    +	{Opt_err, NULL}
    +};
     
     static int
     prlfs_parse_mount_options(char *options, struct prlfs_sb_info *sbi)
     {
    +	substring_t args[MAX_OPT_ARGS];
     	int ret = 0;
    -	char *opt, *val;
    +	int val;
    +	char *opt;
     
     	DPRINTK("ENTER\n");
     #if LINUX_VERSION_CODE < KERNEL_VERSION(2,6,29)
    @@ -70,35 +68,54 @@
     	sbi->ttl = HZ;
     
     	if (!options)
    -	       goto out;
    +		goto out;
     
    -	while (!ret && (opt = strsep(&options, ",")) != NULL)
    +	while (!ret && ((opt = strsep(&options, ",")) != NULL))
     	{
    +		int token;
     		if (!*opt)
     			continue;
     
    -		val = strchr(opt, '=');
    -		if (val) {
    -			*(val++) = 0;
    -			if (strlen(val) == 0)
    -				val = NULL;
    -		}
    -		if (!strcmp(opt, "ttl") && val)
    -			ret = prlfs_strtoui(val, &sbi->ttl);
    -		else if (!strcmp(opt, "uid") && val)
    -			ret = prlfs_strtoui(val, &sbi->uid);
    -		else if (!strcmp(opt, "gid") && val)
    -			ret = prlfs_strtoui(val, &sbi->gid);
    -		else if (!strcmp(opt, "nls") && val)
    -			strncpy(sbi->nls, val, LOCALE_NAME_LEN - 1);
    -		else if (!strcmp(opt, "share"))
    +		token = match_token(opt, prlfs_tokens, args);
    +		switch (token) {
    +		case Opt_uid:
    +			if (!(ret = match_int(&args[0], &val)))
    +#if LINUX_VERSION_CODE >= KERNEL_VERSION(3,5,0)
    +			sbi->uid = KUIDT_INIT(val);
    +#else
    +			sbi->uid = val;
    +#endif
    +			break;
    +		case Opt_gid:
    +			if (!(ret = match_int(&args[0], &val)))
    +#if LINUX_VERSION_CODE >= KERNEL_VERSION(3,5,0)
    +			sbi->gid = KGIDT_INIT(val);
    +#else
    +			sbi->gid = val;
    +#endif
    +			break;
    +		case Opt_ttl:
    +			if (!(ret = match_int(&args[0], &val)))
    +				sbi->ttl = val;
    +			break;
    +		case Opt_nls:
    +			if (!match_strlcpy(sbi->nls, &args[0], LOCALE_NAME_LEN - 1))
    +				ret = -EINVAL;
    +			break;
    +		case Opt_share:
     			sbi->share = 1;
    -		else if (!strcmp(opt, "plain"))
    +			break;
    +		case Opt_plain:
     			sbi->plain = 1;
    -		else if (!strcmp(opt, "sf") && val)
    -			strncpy(sbi->name, val, sizeof(sbi->name));
    -		else
    +			break;
    +		case Opt_sf:
    +			if (!match_strlcpy(sbi->name, &args[0], sizeof(sbi->name)))
    +				ret = -EINVAL;
    +			break;
    +		default:
     			ret = -EINVAL;
    +		}
    +		DPRINTK("PARSE interating %d:%d:%s\n", token, val, args[0]);
     	}
     out:
     	DPRINTK("EXIT returning %d\n", ret);
    diff -Nru prl_fs.orig/SharedFolders/Interfaces/sf_lin.h prl_fs/SharedFolders/Interfaces/sf_lin.h
    --- prl_fs.orig/SharedFolders/Interfaces/sf_lin.h	2013-11-11 18:11:49.000000000 +0200
    +++ prl_fs/SharedFolders/Interfaces/sf_lin.h	2013-11-29 03:11:48.924415600 +0200
    @@ -40,8 +40,13 @@
     	unsigned long long mtime;
     	unsigned long long ctime;
     	unsigned int mode;
    -	unsigned int uid;
    -	unsigned int gid;
    +#if LINUX_VERSION_CODE >= KERNEL_VERSION(3,5,0)
    +	kuid_t uid;
    +	kgid_t gid;
    +#else
    +	uid_t uid;
    +	gid_t gid;
    +#endif
     	unsigned int valid;
     } PACKED;
     SFLIN_CHECK_SIZE(prlfs_attr, sizeof(struct prlfs_attr), 48)
    
    (Sorry for "stealing" formatting from similar post)
     
    Last edited: Nov 29, 2013
  2. jeanjd63

    jeanjd63 Bit Poster

    Messages:
    10
    Hello

    Thanks you it's works perfect.

    Bye
     
  3. junkyudog

    junkyudog Bit Poster

    Messages:
    1
    help

    Hi folks,

    I'm a complete linux novice... how do I 'patch' the parallels tools? I'm running Parallels 8 on an retina mbp. I'm trying to install parallels tools on a kali linux running 3.12 kernel.

    I tried creating a parallels-tools-linux-3.12-prl-fs-9.0.23350.941886.patch file using the attached code.

    But I keep getting errors throughout. I need some help please.

    Thanks in advance!
     
  4. jeanjd63

    jeanjd63 Bit Poster

    Messages:
    10
    Hello
    For this patch Parallels 9 is indispensable.
    Bye
     
  5. fullone

    fullone

    Messages:
    1
    almost there..

    Hello guys,

    Here is my parallels-tools-install.log


    Code:
    Qua Jan 22 16:37:58 BRT 2014
    Start installation or upgrade of Guest Tools
    new version of parallels tools
    Installed Guest Tools were not found
    Perform installation into the /usr/lib/parallels-tools directory
    cat: /usr/lib/parallels-tools/kmods/../version: Arquivo ou diretório não encontrado
    /root/ptools/installer/install-kmods.sh: 41: [: Illegal number: 12-kali1-amd64
    Start installation of prl_eth kernel module
    make: Entrando no diretório `/usr/lib/parallels-tools/kmods'
    cd prl_eth/pvmnet && make
    make[1]: Entrando no diretório `/usr/lib/parallels-tools/kmods/prl_eth/pvmnet'
    make -C /lib/modules/3.12-kali1-amd64/build M=/usr/lib/parallels-tools/kmods/prl_eth/pvmnet
    make[2]: Entrando no diretório `/usr/src/linux-headers-3.12-kali1-amd64'
      LD      /usr/lib/parallels-tools/kmods/prl_eth/pvmnet/built-in.o
      CC [M]  /usr/lib/parallels-tools/kmods/prl_eth/pvmnet/pvmnet.o
      LD [M]  /usr/lib/parallels-tools/kmods/prl_eth/pvmnet/prl_eth.o
      Building modules, stage 2.
      MODPOST 1 modules
      CC      /usr/lib/parallels-tools/kmods/prl_eth/pvmnet/prl_eth.mod.o
      LD [M]  /usr/lib/parallels-tools/kmods/prl_eth/pvmnet/prl_eth.ko
    make[2]: Saindo do diretório `/usr/src/linux-headers-3.12-kali1-amd64'
    make[1]: Saindo do diretório `/usr/lib/parallels-tools/kmods/prl_eth/pvmnet'
    cd prl_tg/Toolgate/Guest/Linux/prl_tg && make
    make[1]: Entrando no diretório `/usr/lib/parallels-tools/kmods/prl_tg/Toolgate/Guest/Linux/prl_tg'
    make -C /lib/modules/3.12-kali1-amd64/build SUBDIRS=/usr/lib/parallels-tools/kmods/prl_tg/Toolgate/Guest/Linux/prl_tg SRCROOT=/usr/lib/parallels-tools/kmods/prl_tg/Toolgate/Guest/Linux/prl_tg modules
    make[2]: Entrando no diretório `/usr/src/linux-headers-3.12-kali1-amd64'
      CC [M]  /usr/lib/parallels-tools/kmods/prl_tg/Toolgate/Guest/Linux/prl_tg/prltg.o
      LD [M]  /usr/lib/parallels-tools/kmods/prl_tg/Toolgate/Guest/Linux/prl_tg/prl_tg.o
      Building modules, stage 2.
      MODPOST 1 modules
      CC      /usr/lib/parallels-tools/kmods/prl_tg/Toolgate/Guest/Linux/prl_tg/prl_tg.mod.o
      LD [M]  /usr/lib/parallels-tools/kmods/prl_tg/Toolgate/Guest/Linux/prl_tg/prl_tg.ko
    make[2]: Saindo do diretório `/usr/src/linux-headers-3.12-kali1-amd64'
    make[1]: Saindo do diretório `/usr/lib/parallels-tools/kmods/prl_tg/Toolgate/Guest/Linux/prl_tg'
    cp -f prl_tg/Toolgate/Guest/Linux/prl_tg/*.symvers prl_fs/SharedFolders/Guest/Linux/prl_fs ||:
    cd prl_fs/SharedFolders/Guest/Linux/prl_fs && make
    make[1]: Entrando no diretório `/usr/lib/parallels-tools/kmods/prl_fs/SharedFolders/Guest/Linux/prl_fs'
    make -C /lib/modules/3.12-kali1-amd64/build M=/usr/lib/parallels-tools/kmods/prl_fs/SharedFolders/Guest/Linux/prl_fs
    make[2]: Entrando no diretório `/usr/src/linux-headers-3.12-kali1-amd64'
      LD      /usr/lib/parallels-tools/kmods/prl_fs/SharedFolders/Guest/Linux/prl_fs/built-in.o
      CC [M]  /usr/lib/parallels-tools/kmods/prl_fs/SharedFolders/Guest/Linux/prl_fs/super.o
      CC [M]  /usr/lib/parallels-tools/kmods/prl_fs/SharedFolders/Guest/Linux/prl_fs/inode.o
      CC [M]  /usr/lib/parallels-tools/kmods/prl_fs/SharedFolders/Guest/Linux/prl_fs/file.o
    /usr/lib/parallels-tools/kmods/prl_fs/SharedFolders/Guest/Linux/prl_fs/file.c:400:2: error: unknown field ‘readdir’ specified in initializer
    /usr/lib/parallels-tools/kmods/prl_fs/SharedFolders/Guest/Linux/prl_fs/file.c:400:2: warning: initialization from incompatible pointer type [enabled by default]
    /usr/lib/parallels-tools/kmods/prl_fs/SharedFolders/Guest/Linux/prl_fs/file.c:400:2: warning: (near initialization for ‘prlfs_dir_fops.flush’) [enabled by default]
    /usr/lib/parallels-tools/kmods/prl_fs/SharedFolders/Guest/Linux/prl_fs/file.c:407:2: error: unknown field ‘readdir’ specified in initializer
    /usr/lib/parallels-tools/kmods/prl_fs/SharedFolders/Guest/Linux/prl_fs/file.c:407:2: warning: initialization from incompatible pointer type [enabled by default]
    /usr/lib/parallels-tools/kmods/prl_fs/SharedFolders/Guest/Linux/prl_fs/file.c:407:2: warning: (near initialization for ‘prlfs_root_fops.flush’) [enabled by default]
    make[5]: ** [/usr/lib/parallels-tools/kmods/prl_fs/SharedFolders/Guest/Linux/prl_fs/file.o] Erro 1
    make[4]: ** [_module_/usr/lib/parallels-tools/kmods/prl_fs/SharedFolders/Guest/Linux/prl_fs] Erro 2
    make[3]: ** [sub-make] Erro 2
    make[2]: ** [all] Erro 2
    make[2]: Saindo do diretório `/usr/src/linux-headers-3.12-kali1-amd64'
    make[1]: ** [all] Erro 2
    make[1]: Saindo do diretório `/usr/lib/parallels-tools/kmods/prl_fs/SharedFolders/Guest/Linux/prl_fs'
    make: ** [installme] Erro 2
    make: Saindo do diretório `/usr/lib/parallels-tools/kmods'
    Error: could not build kernel modules
    Error: failed to install kernel modules
    2014-01-22T16:38:02-0300: execCmd: ./install --install [143]
    2014-01-22T16:38:02-0300: Error: An error occurred when installing Parallels Tools. Please go to /var/log/parallels-tools-install.log for more information.
    2014-01-22T16:38:06-0300: Exiting with code 1
    What am I doing wrong?
    Thanks
     
  6. Marcus Tomlinson

    Marcus Tomlinson

    Messages:
    2
    Brilliant! Thanks eugenesan! :)
     
  7. manuel SPRAUL

    manuel SPRAUL

    Messages:
    3
    Hello,

    i have the version 9.024172.951362 and the patch is not present in the kmods folder .

    Everybody can't help me please ?
     
  8. jeanjd63

    jeanjd63 Bit Poster

    Messages:
    10
    Hello

    The patch in post #1 works fine with Parallels Tools 9.0.24172.

    Bye
     
  9. manuel SPRAUL

    manuel SPRAUL

    Messages:
    3
    ok cant' you say me how i must the patch in kmods folder other in prl_fs.orig/SharedFolders/Guest/Linux/prl_fs folders ?

    i have create the patch fil but nothing works ...

    thanks
     
  10. jeanjd63

    jeanjd63 Bit Poster

    Messages:
    10
    All is explain post#1
     
  11. manuel SPRAUL

    manuel SPRAUL

    Messages:
    3
    I know but when i would make the redirection from the file to the command i have a error that the file don't existe.

    Sorry i debute with debian ...
     
  12. jeanjd63

    jeanjd63 Bit Poster

    Messages:
    10

    When you create the patch, you name it parallels-tools-linux-3.12-prl-fs-9.0.23350.941886.patch
    and you copy it in directory : /tmp/Parallels\ Tools/kmods (where you have extract prl_mod.tar.gz)
    Il the file patch is named # you can adapt the commande line :
    patch -p1 -d prl_fs < file_name_of.patch
     
  13. pete-woods

    pete-woods

    Messages:
    6
  14. antenando

    antenando

    Messages:
    1
    Let me ask you, if I may. Does the name of the actual file (parallels-tools-linux-3.12-prl-fs-9.0.23350.941886.patch) has anything to do with the effectiveness of the patch or can I name it anything I want?

    Cheers
     
  15. eugenesan

    eugenesan

    Messages:
    5
    No, patch file name is absolutely irrelevant.
     
  16. Mark Fine

    Mark Fine Bit Poster

    Messages:
    68
    Applied the patch to a Fedora 19 (kernel 3.12.11-201) system under Parallells 9.0.24172 and it worked like a champ.

    Tried to apply it to a Fedora 20 (kernel 3.13.3-201) system, but gdm bounces four times and quits. Even tried removing and reinstalling. No luck there, so far. Judging from Xorg.0.log, there might be an issue with prlmouse masquerading under Generic Explorer Mouse. /dev/input/mouse0 never gets generated: "No input driver specified, ignoring this device."
     
  17. Mark Fine

    Mark Fine Bit Poster

    Messages:
    68
    ...check that, 19 had the same note in the log. However, PRL_GLX had a lot of stuff that ran in 19 that never seemed to kick off in 20, which seems to be the primary difference in the logs here.
     
  18. Mark Fine

    Mark Fine Bit Poster

    Messages:
    68
    Sure enough, kernel 3.13.4-200 was just released, amongst other things. Updated the kernel, rebuilt/updated Parallel Tools, and voila... now it works with Fedora 20. It's quirky in that the display settings don't completely recognize it, nor does it remember the last screen size, but at least gdm no longer crashes.
     
  19. jones

    jones

    Messages:
    5
    Worked great -- many thanks, eugenesan!!
     
  20. ShineL

    ShineL

    Messages:
    1
    Hello,
    This method works fine with linux kali 3.12 kernel.
    First, copy the code to a file and rename as "parallels-tools-linux-3.12-prl-fs-9.0.23350.941886.patch"; then do as eugenesan said.
    Second, this patch do work with latest parallels desktop version 9.024172.951362 and it's parallels tools, but in my apple mac air, a message will popup every time when I restart it, says that the system will not work at resolution 1280x800. I will check it when I free.
    Third, after you create the patch file, you have to move it into the directory of kmods.

    Thanks for eugenesan .

    Bye
     

Share This Page