Openoffice pipe (сокет домена unix) где-то, кроме /tmp?

Можно заставить Openoffice принимать соединения UNO через сокет домена unix с:

$soffice -headless -invisible -nocrashreport -nodefault -nologo -nofirststartwizard -norestore -conversionmode -accept='pipe,name=marcin_OOffice;urp;StarOffice.ComponentContext'

netstat показывает, что доменный сокет создается в /tmp/OSL_PIPE_1001_marcin_OOffice, Это нормально, но так как я буду запускать это на общем хосте, я бы хотел, чтобы сокет был где-то еще, например, на моем домашнем диске. Тем не менее, передавая полный путь к файлу (относительный или абсолютный) в качестве name параметр приводит к тому, что сокет не создается.

Есть ли способ, которым я могу повлиять на то, где создается сокет, например, с помощью переменной окружения?

РЕДАКТИРОВАТЬ: Настройка TMP а также TMPDIR Переменные окружения не влияют на это поведение. Я запускаю это на Linux.

2 ответа

Решение

Поскольку, похоже, не существует "официального" способа контроля того, где создается сокет, вы можете пойти "кувалдой, чтобы взломать", написав свой собственный общий объект, который вставляется в connect() и переписывает любой AF_FILE адреса в /tmp:

#define _GNU_SOURCE
#include <sys/types.h>
#include <sys/socket.h>
#include <assert.h>
#include <linux/un.h>
#include <dlfcn.h>
#include <stdlib.h>
#include <string.h>

int connect(int sockfd, const struct sockaddr *addr,
            socklen_t addrlen) 
{
  static int (*real_connect)(int, const struct sockaddr *, socklen_t) = NULL;
  if (!real_connect)
    real_connect = dlsym(RTLD_NEXT, "connect");

  if (addr->sa_family == AF_FILE) {
    // mutate sockaddr
    assert(addrlen >= sizeof(struct sockaddr_un));
    const struct sockaddr_un u = { AF_UNIX, "/foo/bar/path" };
    // but only if it is in /tmp
    if (!strncmp(((const struct sockaddr_un*)addr)->sun_path, "/tmp", 4)) {
      return real_connect(sockfd, (const struct sockaddr*)&u, sizeof u);
    }
  }
  return real_connect(sockfd, addr, addrlen);
}

Компилировать с:

gcc -Wall -Wextra test.c -ldl -shared -o interpose.so -fPIC

А затем запустите как:

LD_PRELOAD=./interpose.so soffice -headless -invisible -nocrashreport -nodefault -nologo -nofirststartwizard -norestore -conversionmode -accept='pipe,name=marcin_OOffice;urp;StarOffice.ComponentContext'

который, кажется, работает от чтения вывода strace (но я понятия не имею, как на самом деле использовать сокет, чтобы доказать, что он действительно работает).

Вы должны вставить между bind() (та же подпись, что и у connect), так как именно здесь создается сокет, а затем клиенты вставляют между connect(),

Другие вопросы по тегам