Iperf3 error unable to create a new stream permission denied

I compile iperf bin for android with NDK r10e. I use LDFLAGS="-fPIE -pie -fuse-ld=bfd" configs to build. But now it said when i use as client or server: iperf3: error - unable to create a...

@Pr0gmaT1k

I compile iperf bin for android with NDK r10e.
I use LDFLAGS=»-fPIE -pie -fuse-ld=bfd» configs to build.

But now it said when i use as client or server:
iperf3: error — unable to create a new stream: No such file or directory

As server, on the client side i get:
iperf3: error — control socket has closed unexpectedly

The only warning that i get at compile time is:
portable_endian.h:133:3: warning: #warning platform not supported [-Wcpp]
portable_endian.h:158:0: warning: «htobe64» redefined [enabled by default]
In file included from /usr/lib/gcc/arm-linux-androideabi/4.7.3/../../../../arm-linux-androideabi/include/endian.h:87:0,
from /usr/lib/gcc/arm-linux-androideabi/4.7.3/../../../../arm-linux-androideabi/include/netinet/in.h:31,
from iperf_udp.c:35:

How can i workaround that ?

@Pr0gmaT1k

also -v said:
iperf 3.1
Linux localhost 3.10.65+ #1 SMP PREEMPT Mon Sep 14 20:33:24 CST 2015 aarch64
Optional features available: CPU affinity setting, IPv6 flow label, TCP congestion algorithm setting, sendfile / zerocopy

@Pr0gmaT1k

Well another interesting things.
When i install Magic iPerf3 from store, the same binaries work.

The iperf3 inside /data/data/com.nextdoordeveloper.miperf.miperf/files/iperf3 even if i copy it in another location.
BUT,
If i delete the app, the issue reappears. with his own binaries that work just before.

@brbsix

I had the same issue after sourcing Iperf3 binaries from he.net — Network Tools. It needed write access to /data/data/net.he.networktools/cache/, which obviously does not exist when the APK is not installed.

So I opened it up in a hex editor, found the template string /data/data/net.he.networktools/cache/iperf3.XXXXXX, and replaced it with the path to a world-writable directory. You’ll have to figure out where you want that to be since AFAIK there is no /tmp in Android. Basically you’ll want to replace the template string with something like ////////////////path/to/writable/dir/iperf3.XXXXXX (you should probably take care to make sure the replacement string is the same length just to be safe).

I didn’t want to go through the trouble of compiling it for Android, but you can also just change it prior to compilation. Also you can obviously disregard the prior comment about matching replacement string length if you go this route.

char buf[] = «/tmp/iperf3.XXXXXX«;

Hope that helps,
Six

@Pr0gmaT1k

It work perfectly with existing binaries.

Android have a writable tmp in /data/local/tmp.

Thanks a lot !

@crearo

Hi I’m trying the exact same thing. How did you get this to work?

I am unable to push the iperf3 binary to /data/local/tmp. here’s the reason

I have tried running the binary from /data/data/app.package/ and i get the same unable to create a new stream: No such file or directory error.

@AndroidPat

It work perfectly with existing binaries.

Android have a writable tmp in /data/local/tmp.

Thanks a lot !

I’m having huge problems making Android version of iPerf3 binaries. I’m wondering if you could share your binaries for different architectures?

@hugoinfante83

matching replacement string length

Thanks for the tip!!!!

@Juliocbr

Hi

I have the same issue, I modified these lines in iperf_api.c according to @brbsix explanation:

char buf[] = "/data/local/tmp/iperf3.XXXXXX";
snprintf(template, sizeof(template) / sizeof(char), "%s", buf);

but when I execute some iperf command using «Runtime.getRuntime().exec(cmd)», I get this error:

...
},
    	"intervals":	[],
    	"end":	{
    	},
    	"error":	"error - unable to create a new stream: Permission denied"
    }
...

Notes: I’m using NDK to compile the iperf3 library and I put the executable file in jniLibs, I change the name of executable, for example «iperf3» to «libiperf3.so». I’m using non rooted device.

@davidBar-On

I creating an Android application that allow to execute some iperf commands. To do that, I got the version 3 of the source code of the IPerf C project and I cross-compile it using those commands :

> make clean
> ./configure --host=arm-linux --prefix=/home/laboPC/Downloads CC=arm-linux-androideabi-gcc CXX=arm-linux-androideabi-g++ CFLAGS="-static" CXXFLAGS="-static" LDFLAGS="-pie -fuse-ld=bfd"
> make

After the cross-compile, I got a binary file that I put in the assets folder in my android project.

For using IPerf from Android, I create a copy of the binary in this way :

private String binariePath = context.getApplicationInfo().dataDir + "/iperf3";

private void setupBinaries(){
     InputStream in = context.getResources().openRawResource(R.raw.iperf3);
     OutputStream out = new FileOutputStream(binariePath);
     byte[] buf = new byte[1024];
     int len;

     while ((len = in.read(buf)) > 0) {
         out.write(buf, 0, len);
     }
     in.close();
     out.flush();
     out.close();
     Runtime.getRuntime().exec("chmod 751 " + binariePath);
}

And then, I using a Runtime object to execute a iperf command like this :

public String runClient (String server, String argument) {
    try {
       setupBinaries();

        process = Runtime.getRuntime().exec(binariePath + " -c " + server + " " + argument);
        BufferedReader reader = new BufferedReader( new InputStreamReader(process.getInputStream()));

        final StringBuilder result = new StringBuilder();
        String line;
        while ((line = reader.readLine()) != null) {
            result.append(line + "n");
        }
        reader.close();
        process.destroy();
        return result.toString();

    } catch (IOException e) {
        Log.d("IPERF", e.getLocalizedMessage());
        return e.getLocalizedMessage();
    }
}

Everythings works fine except in Android 7.0. When I runnig my app on the Nexus 5X in Android 7, the iperf command seems not to be execute and my result variable is empty.

I checked that the Runtime.exec() works fine in android 7 and that the binary is correctly copy in the app data directory.

Is everyone has an idea what is wrong in my process ? Is my commands fo compile IPerf project is correct ?

Thanks for your help.

EDIT

I found in the followings threads that Android 6.0 and higher can execute binaries that are compiled with the -fPIC option :

android ndk: are -fPIC and -pie mututally exclusive?

Position Independent Executables and Android Lollipop

So I tried to compile my C project by using this command line :

./configure —host=arm-linux —prefix=/home/laboPC/Downloads CC=arm-linux-androideabi-gcc CXX=arm-linux-androideabi-g++ CFLAGS=»-static -fPIC» CXXFLAGS=»-static» LDFLAGS=»-pie -fuse-ld=bfd»

I think there is something wrong about my command line but I don’t know what. Is anybody can help me to identifiate what I wrong in my command line ?

Iperf is a
free open-source software tool that provides a capability
to measure the throughput between two hosts using both
Transmission Control Protocol (TCP) and

User Datagram Protocol (UDP) data streams. The software can be run in
either server or

client mode. To determine the network bandwidth available between two
systems, you can run iperf in server mode on one of the systems and in
client mode on the other.

The software is available for a variety of operating systems. You can
download iPerf binaries from
iPerf — The network bandwidth
measurement tool for the following operating systems:

  1. Microsoft Windows
  2. Android
  3. iPhone / iPad
  4. Apple OS X
  5. Download iPerf for Ubuntu / Debian / Mint
  6. Download iPerf for Fedora / Red Hat / CentOS
  7. Download iPerf for openSUSE
  8. Download iPerf for Arch Linux
  9. Download iPerf for FreeBSD

You can also download the C++
source
code from that page. Alternatively, if you are using a
Linux
distribution, you may be able to install it using a standard

package management tool for the particular distribution of Linux that you
are using. E.g., see
Installing iperf on CentOS for instructions on how to install the
software with
yum.

If you install the software on two systems you control, you can test
between those systems. There are also
public iPerf3 servers
in various parts of the world with which you can test. Those systems are
running in server mode, so you use client mode on your local system
when testing with them. You specify client mode with the -c
option. You can see the available options for the program by issuing the
command iperf -h from a
command prompt while in the
directory where you installed the software on the Microsoft Windows system.

Generic Category (English)120x600

C:>iperf3
Usage: iperf [-s|-c host] [options]
       iperf [-h|--help] [-v|--version]

Server or Client:
  -p, --port      #         server port to listen on/connect to
  -f, --format    [kmgKMG]  format to report: Kbits, Mbits, KBytes, MBytes
  -i, --interval  #         seconds between periodic bandwidth reports
  -F, --file name           xmit/recv the specified file
  -B, --bind      <host>    bind to a specific interface
  -V, --verbose             more detailed output
  -J, --json                output in JSON format
  --logfile f               send output to a log file
  -d, --debug               emit debugging output
  -v, --version             show version information and quit
  -h, --help                show this message and quit
Server specific:
  -s, --server              run in server mode
  -D, --daemon              run the server as a daemon
  -I, --pidfile file        write PID file
  -1, --one-off             handle one client connection then exit
Client specific:
  -c, --client    <host>    run in client mode, connecting to <host>
  -u, --udp                 use UDP rather than TCP
  -b, --bandwidth #[KMG][/#] target bandwidth in bits/sec (0 for unlimited)
                            (default 1 Mbit/sec for UDP, unlimited for TCP)
                            (optional slash and packet count for burst mode)
  -t, --time      #         time in seconds to transmit for (default 10 secs)
  -n, --bytes     #[KMG]    number of bytes to transmit (instead of -t)
  -k, --blockcount #[KMG]   number of blocks (packets) to transmit (instead of -
t or -n)
  -l, --len       #[KMG]    length of buffer to read or write
                            (default 128 KB for TCP, 8 KB for UDP)
  --cport         <port>    bind to a specific client port (TCP and UDP, default
: ephemeral port)
  -P, --parallel  #         number of parallel client streams to run
  -R, --reverse             run in reverse mode (server sends, client receives)
  -w, --window    #[KMG]    set window size / socket buffer size
  -M, --set-mss   #         set TCP/SCTP maximum segment size (MTU - 40 bytes)
  -N, --no-delay            set TCP/SCTP no delay, disabling Nagle's Algorithm
  -4, --version4            only use IPv4
  -6, --version6            only use IPv6
  -S, --tos N               set the IP 'type of service'
  -Z, --zerocopy            use a 'zero copy' method of sending data
  -O, --omit N              omit the first n seconds
  -T, --title str           prefix every output line with this string
  --get-server-output       get results from server
  --udp-counters-64bit      use 64-bit counters in UDP test packets

[KMG] indicates options that support a K/M/G suffix for kilo-, mega-, or giga-

iperf3 homepage at: http://software.es.net/iperf/
Report bugs to:     https://github.com/esnet/iperf

C:Program Filesiperf>

For a Microsoft Windows system, you need only
download the zip file
for Windows, unzip the contents of the file, and then move the two files
within the zip file, which are cygwin1.dll and
iperf3.exe, if you downloaded a version 3 release of the
software, to whatever directory you wish to keep the program in. Note: you
can’t test between a host running version 3 and one running version 2; both
systems need to be running a version with the same major version unumber, e.g.,
a 2.x or 3.x version.

The download site offers 32-bit and
64-bit
versions of the software. If you have a 32-bit version of Windows, you
should use a 32-bit version and if you have a 64-bit version of Windows you
should use the 64-bit version. If you don’t know whether your version of
Microsoft Windows is 32-bit or 64-bit, see
Determining if your version
of Windows is a 32-bit or 64-bit version.

To test with a public iperf3 server, bouygues.testdebit.info, located in
France, I could issue the command iperf3 -c bouygues.testdebit.info
using the iperf3 software installed on a Microsoft Windows system.
Note: if you see the error message below, you may need to open a command
prompt window in administrator mode to be able to test with iperf on
the Windows system.

C:Program Filesiperf>iperf3 -c bouygues.testdebit.info
Connecting to host bouygues.testdebit.info, port 5201
iperf3: error - unable to create a new stream: Permission denied

C:Program Filesiperf>

To open a command prompt window where you can run the command with
administrator permissions, see the instructions at
Obtaining a Command Prompt on a
Windows 8 System; the steps for other versions of Windows are similar.

If you run the software in client mode, you will see output similar to
the following, which is from a test with the public test server
bouygues.testdebit.info.

C:Program Filesiperf>iperf3 -c bouygues.testdebit.info
Connecting to host bouygues.testdebit.info, port 5201
[  4] local 192.168.0.6 port 49894 connected to 89.84.127.53 port 5201
[ ID] Interval           Transfer     Bandwidth
[  4]   0.00-1.00   sec   512 KBytes  4.19 Mbits/sec
[  4]   1.00-2.00   sec  1.00 MBytes  8.39 Mbits/sec
[  4]   2.00-3.00   sec   896 KBytes  7.35 Mbits/sec
[  4]   3.00-4.00   sec  1.00 MBytes  8.39 Mbits/sec
[  4]   4.00-5.00   sec   896 KBytes  7.34 Mbits/sec
[  4]   5.00-6.00   sec   896 KBytes  7.33 Mbits/sec
[  4]   6.00-7.00   sec  1.00 MBytes  8.39 Mbits/sec
[  4]   7.00-8.00   sec   896 KBytes  7.34 Mbits/sec
[  4]   8.00-9.00   sec   896 KBytes  7.34 Mbits/sec
[  4]   9.00-10.00  sec  1.00 MBytes  8.40 Mbits/sec
- - - - - - - - - - - - - - - - - - - - - - - - -
[ ID] Interval           Transfer     Bandwidth
[  4]   0.00-10.00  sec  8.88 MBytes  7.44 Mbits/sec                  sender
[  4]   0.00-10.00  sec  8.87 MBytes  7.44 Mbits/sec                  receiver

iperf Done.

C:Program Filesiperf>

For this particular test, the client system could achieve a bandwidth
of about 7 — 8 Mbs, which was fairly good considering the client system
was constrained by a 10 Mbs
local area network
(LAN) connection.

Мне нужно сделать приложение для Android, которое запускает библиотеку iperf3, поэтому я скомпилировал «iperf3» с помощью android-ndk-r20 с изменениями, сделанными в

Iperf_api.c

char buf[] = "/tmp/iperf3.XXXXXX"; Я заменил char buf[] = "/data/local/tmp/iperf3.XXXXXX";, понял, как упаковать его с моим приложением для Android и запустить. Но я не знаю, как запустить его без прав «su» (root).

Хорошо работающий код:

ArrayList<String> commandLine = new ArrayList<String>();
commandLine.add("su");
commandLine.add("-c");
commandLine.add(getApplicationContext().getApplicationInfo().nativeLibraryDir+"/libiperf3.so -c speedtest.hostkey.ru -t 10 -i 5 -P 3 -d");
Process process = Runtime.getRuntime().exec(commandLine.toArray(new String[0]));

Он хорошо работает с «su», но мне нужно, чтобы он работал без рута. Когда я пытаюсь использовать тот же код, но с «su», замененным на «sh», я получаю эту ошибку:

iperf3: error - unable to create a new stream: Permission denied

Я не знаю, как заставить это работать, есть некоторые приложения, которые используют iperf3 в Google Play Store без прав root, так что это возможно. Что я делаю не так?

2 ответа

Лучший ответ

Я понял, как заставить это работать. Перед компиляцией «iperf3» необходимо изменить следующую строку в «iperf_api.c»

char buf[] = "/tmp/iperf3.XXXXXX";

В char buf[] = "/data/data/your.package.name/cache/iperf3.XXXXXX"; И это работает отлично! Надеюсь, я кому-то помог.


2

ArtemYashin
27 Окт 2019 в 09:45

Это также работает, когда вы устанавливаете любую из следующих переменных среды в доступный для записи каталог (например, cacheDir): TMPDIR или TEMP или TMP

Например: Os.setenv("TEMP", CACHE_DIR, true)

Временный каталог проверяется в функции iperf_api.c iperf_new_stream.


0

Farhad Zamani
1 Апр 2020 в 18:34

Понравилась статья? Поделить с друзьями:
  • Iperf3 error unable to connect to server connection timed out
  • Iperf3 error unable to connect to server connection refused
  • Iperf3 error received an unknown control message
  • Iperf3 error control socket has closed unexpectedly
  • Ipdl protocol error handler returned error code