Skip to content

Commit d2e0f53

Browse files
committed
[JENKINS-32624] [JENKINS-27152] Use a standardized temporary directory when possible.
1 parent c4d2197 commit d2e0f53

File tree

8 files changed

+75
-23
lines changed

8 files changed

+75
-23
lines changed

src/main/java/com/cloudbees/jenkins/plugins/sshagent/RemoteAgentFactory.java

Lines changed: 16 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -25,8 +25,11 @@
2525
package com.cloudbees.jenkins.plugins.sshagent;
2626

2727
import hudson.ExtensionPoint;
28+
import hudson.FilePath;
2829
import hudson.Launcher;
30+
import hudson.Util;
2931
import hudson.model.TaskListener;
32+
import javax.annotation.CheckForNull;
3033

3134
/**
3235
* Extension point for ssh-agent providers.
@@ -48,13 +51,25 @@ public abstract class RemoteAgentFactory implements ExtensionPoint {
4851
*/
4952
public abstract boolean isSupported(Launcher launcher, TaskListener listener);
5053

54+
@Deprecated
55+
public RemoteAgent start(Launcher launcher, TaskListener listener) throws Throwable {
56+
return start(launcher, listener, null);
57+
}
58+
5159
/**
5260
* Start a ssh-agent on the specified launcher.
5361
*
5462
* @param launcher the launcher on which to start a ssh-agent.
5563
* @param listener a listener for any diagnostics.
64+
* @param temp a temporary directory to use; null if unspecified
5665
* @return the agent.
5766
* @throws Throwable if the agent cannot be started.
5867
*/
59-
public abstract RemoteAgent start(Launcher launcher, TaskListener listener) throws Throwable;
68+
public /*abstract*/ RemoteAgent start(Launcher launcher, TaskListener listener, @CheckForNull FilePath temp) throws Throwable {
69+
if (Util.isOverridden(RemoteAgentFactory.class, getClass(), "start", Launcher.class, TaskListener.class)) {
70+
return start(launcher, listener);
71+
} else {
72+
throw new AbstractMethodError("you must implement the start method");
73+
}
74+
}
6075
}

src/main/java/com/cloudbees/jenkins/plugins/sshagent/SSHAgentBuildWrapper.java

Lines changed: 10 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -32,6 +32,7 @@
3232
import edu.umd.cs.findbugs.annotations.NonNull;
3333
import edu.umd.cs.findbugs.annotations.Nullable;
3434
import hudson.Extension;
35+
import hudson.FilePath;
3536
import hudson.Launcher;
3637
import hudson.Util;
3738
import hudson.model.AbstractBuild;
@@ -56,6 +57,7 @@
5657
import java.util.LinkedHashSet;
5758
import java.util.List;
5859
import java.util.Map;
60+
import javax.annotation.CheckForNull;
5961
import javax.annotation.Nonnull;
6062
import jenkins.model.Jenkins;
6163
import org.apache.commons.lang.StringUtils;
@@ -243,7 +245,7 @@ public Environment setUp(AbstractBuild build, final Launcher launcher, BuildList
243245
private SSHAgentEnvironment createSSHAgentEnvironment(AbstractBuild build, Launcher launcher, BuildListener listener)
244246
throws IOException, InterruptedException {
245247
try {
246-
return new SSHAgentEnvironment(launcher, listener);
248+
return new SSHAgentEnvironment(launcher, listener, build.getWorkspace());
247249
} catch (IOException e) {
248250
throw new IOException2(Messages.SSHAgentBuildWrapper_CouldNotStartAgent(), e);
249251
} catch (InterruptedException e) {
@@ -334,6 +336,11 @@ public SSHAgentEnvironment(Launcher launcher, final BuildListener listener,
334336
}
335337
}
336338

339+
@Deprecated
340+
public SSHAgentEnvironment(Launcher launcher, final BuildListener listener) throws Throwable {
341+
this(launcher, listener, (FilePath) null);
342+
}
343+
337344
/**
338345
* Construct the environment and initialize on the remote node.
339346
*
@@ -342,15 +349,15 @@ public SSHAgentEnvironment(Launcher launcher, final BuildListener listener,
342349
* @throws Throwable if things go wrong.
343350
* @since 1.9
344351
*/
345-
public SSHAgentEnvironment(Launcher launcher, final BuildListener listener) throws Throwable {
352+
public SSHAgentEnvironment(Launcher launcher, BuildListener listener, @CheckForNull FilePath workspace) throws Throwable {
346353
RemoteAgent agent = null;
347354
listener.getLogger().println("[ssh-agent] Looking for ssh-agent implementation...");
348355
Map<String, Throwable> faults = new LinkedHashMap<String, Throwable>();
349356
for (RemoteAgentFactory factory : Jenkins.getActiveInstance().getExtensionList(RemoteAgentFactory.class)) {
350357
if (factory.isSupported(launcher, listener)) {
351358
try {
352359
listener.getLogger().println("[ssh-agent] " + factory.getDisplayName());
353-
agent = factory.start(launcher, listener);
360+
agent = factory.start(launcher, listener, workspace != null ? SSHAgentStepExecution.tempDir(workspace) : null);
354361
break;
355362
} catch (Throwable t) {
356363
faults.put(factory.getDisplayName(), t);

src/main/java/com/cloudbees/jenkins/plugins/sshagent/SSHAgentStepExecution.java

Lines changed: 11 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -4,9 +4,11 @@
44
import com.cloudbees.plugins.credentials.CredentialsProvider;
55
import com.google.inject.Inject;
66
import hudson.EnvVars;
7+
import hudson.FilePath;
78
import hudson.Launcher;
89
import hudson.model.Run;
910
import hudson.model.TaskListener;
11+
import hudson.slaves.WorkspaceList;
1012
import hudson.util.Secret;
1113
import jenkins.model.Jenkins;
1214
import org.apache.commons.lang.StringUtils;
@@ -32,6 +34,9 @@ public class SSHAgentStepExecution extends AbstractStepExecutionImpl {
3234
@StepContextParameter
3335
private transient Launcher launcher;
3436

37+
@StepContextParameter
38+
private transient FilePath workspace;
39+
3540
@Inject(optional = true)
3641
private SSHAgentStep step;
3742

@@ -82,6 +87,11 @@ public void onResume() {
8287
}
8388
}
8489

90+
// TODO use https://github.com/jenkinsci/jenkins/pull/2066
91+
static FilePath tempDir(FilePath ws) {
92+
return ws.sibling(ws.getName() + System.getProperty(WorkspaceList.class.getName(), "@") + "tmp");
93+
}
94+
8595
private static class Callback extends BodyExecutionCallback {
8696

8797
private static final long serialVersionUID = 1L;
@@ -149,7 +159,7 @@ private void initRemoteAgent() throws IOException {
149159
if (factory.isSupported(launcher, listener)) {
150160
try {
151161
listener.getLogger().println("[ssh-agent] " + factory.getDisplayName());
152-
agent = factory.start(launcher, listener);
162+
agent = factory.start(launcher, listener, tempDir(workspace));
153163
break;
154164
} catch (Throwable t) {
155165
faults.put(factory.getDisplayName(), t);

src/main/java/com/cloudbees/jenkins/plugins/sshagent/jna/AgentServer.java

Lines changed: 21 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -18,8 +18,7 @@
1818
*/
1919
package com.cloudbees.jenkins.plugins.sshagent.jna;
2020

21-
import java.security.PublicKey;
22-
import java.util.List;
21+
import edu.umd.cs.findbugs.annotations.SuppressFBWarnings;
2322
import jnr.enxio.channels.NativeSelectorProvider;
2423
import jnr.posix.POSIXFactory;
2524
import jnr.unixsocket.UnixServerSocket;
@@ -41,12 +40,10 @@
4140
import java.util.Iterator;
4241
import java.util.logging.Level;
4342
import java.util.logging.Logger;
44-
import org.apache.sshd.common.util.Pair;
43+
import javax.annotation.CheckForNull;
4544
import org.apache.sshd.common.util.buffer.Buffer;
4645
import org.apache.sshd.common.util.buffer.ByteArrayBuffer;
4746

48-
import static org.apache.sshd.agent.SshAgentConstants.SSH2_AGENTC_REQUEST_IDENTITIES;
49-
import static org.apache.sshd.agent.SshAgentConstants.SSH2_AGENT_IDENTITIES_ANSWER;
5047

5148

5249
/**
@@ -62,13 +59,15 @@ public class AgentServer {
6259
private UnixServerSocket socket;
6360
private Selector selector;
6461
private volatile boolean selectable = true;
62+
private final @CheckForNull File temp;
6563

66-
public AgentServer() {
67-
this(new AgentImpl());
64+
public AgentServer(File temp) {
65+
this(new AgentImpl(), temp);
6866
}
6967

70-
public AgentServer(SshAgent agent) {
68+
public AgentServer(SshAgent agent, File temp) {
7169
this.agent = agent;
70+
this.temp = temp;
7271
}
7372

7473
public SshAgent getAgent() {
@@ -87,6 +86,9 @@ public String start() throws Exception {
8786
channel.register(selector, SelectionKey.OP_ACCEPT, new SshAgentServerSocketHandler());
8887

8988
POSIXFactory.getPOSIX().chmod(authSocket, 0600);
89+
if (!new File(authSocket).exists()) {
90+
throw new IllegalStateException("failed to create " + authSocket + " of length " + authSocket.length() + " (check UNIX_PATH_MAX)");
91+
}
9092

9193
thread = new Thread(new AgentSocketAcceptor(), "SSH Agent socket acceptor " + authSocket);
9294
thread.setDaemon(true);
@@ -130,14 +132,22 @@ public void run() {
130132
}
131133
}
132134

133-
static String createLocalSocketAddress() throws IOException {
135+
@SuppressFBWarnings(value="RV_RETURN_VALUE_IGNORED_BAD_PRACTICE", justification="createTempFile will fail anyway if there is a problem with mkdirs")
136+
private String createLocalSocketAddress() throws IOException {
134137
String name;
138+
if (temp != null) {
139+
temp.mkdirs();
140+
}
135141
if (OsUtils.isUNIX()) {
136-
File socket = File.createTempFile("jenkins", ".jnr");
142+
File socket = File.createTempFile("ssh", "", temp);
143+
if (socket.getAbsolutePath().length() >= /*UNIX_PATH_MAX*/108) {
144+
LOGGER.log(Level.WARNING, "Cannot use {0} due to UNIX_PATH_MAX; falling back to system temp dir", socket);
145+
socket = File.createTempFile("ssh", "");
146+
}
137147
FileUtils.deleteQuietly(socket);
138148
name = socket.getAbsolutePath();
139149
} else {
140-
File socket = File.createTempFile("jenkins", ".jnr");
150+
File socket = File.createTempFile("ssh", "", temp);
141151
FileUtils.deleteQuietly(socket);
142152
name = "\\\\.\\pipe\\" + socket.getName();
143153
}

src/main/java/com/cloudbees/jenkins/plugins/sshagent/jna/JNRRemoteAgent.java

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -27,6 +27,7 @@
2727
import com.cloudbees.jenkins.plugins.sshagent.Messages;
2828
import com.cloudbees.jenkins.plugins.sshagent.RemoteAgent;
2929
import hudson.model.TaskListener;
30+
import java.io.File;
3031
import org.apache.sshd.common.util.SecurityUtils;
3132
import org.bouncycastle.openssl.PEMKeyPair;
3233
import org.bouncycastle.openssl.jcajce.JcePEMDecryptorProviderBuilder;
@@ -38,6 +39,7 @@
3839
import java.io.IOException;
3940
import java.io.StringReader;
4041
import java.security.KeyPair;
42+
import javax.annotation.CheckForNull;
4143

4244
/**
4345
* An implementation that uses Apache SSH to provide the Agent over JNR's UnixSocket implementation.
@@ -62,9 +64,9 @@ public class JNRRemoteAgent implements RemoteAgent {
6264
* @param listener the listener.
6365
* @throws Exception if the agent could not start.
6466
*/
65-
public JNRRemoteAgent(TaskListener listener) throws Exception {
67+
public JNRRemoteAgent(TaskListener listener, @CheckForNull File temp) throws Exception {
6668
this.listener = listener;
67-
agent = new AgentServer();
69+
agent = new AgentServer(temp);
6870
socket = agent.start();
6971
}
7072

src/main/java/com/cloudbees/jenkins/plugins/sshagent/jna/JNRRemoteAgentFactory.java

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -27,6 +27,7 @@
2727
import com.cloudbees.jenkins.plugins.sshagent.RemoteAgent;
2828
import com.cloudbees.jenkins.plugins.sshagent.RemoteAgentFactory;
2929
import hudson.Extension;
30+
import hudson.FilePath;
3031
import hudson.Launcher;
3132
import hudson.model.TaskListener;
3233

@@ -57,8 +58,8 @@ public boolean isSupported(Launcher launcher, final TaskListener listener) {
5758
* {@inheritDoc}
5859
*/
5960
@Override
60-
public RemoteAgent start(Launcher launcher, final TaskListener listener) throws Throwable {
61-
return launcher.getChannel().call(new JNRRemoteAgentStarter(listener));
61+
public RemoteAgent start(Launcher launcher, final TaskListener listener, FilePath temp) throws Throwable {
62+
return launcher.getChannel().call(new JNRRemoteAgentStarter(listener, temp != null ? temp.getRemote() : null));
6263
}
6364

6465
}

src/main/java/com/cloudbees/jenkins/plugins/sshagent/jna/JNRRemoteAgentStarter.java

Lines changed: 7 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -30,6 +30,8 @@
3030

3131
import hudson.model.TaskListener;
3232
import hudson.remoting.Channel;
33+
import java.io.File;
34+
import javax.annotation.CheckForNull;
3335

3436
/**
3537
* Callable to start the remote agent.
@@ -47,20 +49,23 @@ public class JNRRemoteAgentStarter extends MasterToSlaveCallable<RemoteAgent, Th
4749
*/
4850
private final TaskListener listener;
4951

52+
private final @CheckForNull String tempDir;
53+
5054
/**
5155
* Constructor.
5256
*
5357
* @param listener the listener to pass to the agent.
5458
*/
55-
public JNRRemoteAgentStarter(TaskListener listener) {
59+
public JNRRemoteAgentStarter(TaskListener listener, String tempDir) {
5660
this.listener = listener;
61+
this.tempDir = tempDir;
5762
}
5863

5964
/**
6065
* {@inheritDoc}
6166
*/
6267
public RemoteAgent call() throws Throwable {
63-
final JNRRemoteAgent instance = new JNRRemoteAgent(listener);
68+
final JNRRemoteAgent instance = new JNRRemoteAgent(listener, tempDir != null ? new File(tempDir) : null);
6469
final Channel channel = Channel.current();
6570
return channel == null ? instance : channel.export(RemoteAgent.class, instance);
6671
}

src/main/java/com/cloudbees/jenkins/plugins/sshagent/mina/MinaRemoteAgentFactory.java

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -28,6 +28,7 @@
2828
import com.cloudbees.jenkins.plugins.sshagent.RemoteAgentFactory;
2929

3030
import hudson.Extension;
31+
import hudson.FilePath;
3132
import hudson.Launcher;
3233
import hudson.model.TaskListener;
3334

@@ -64,7 +65,8 @@ public boolean isSupported(Launcher launcher, final TaskListener listener) {
6465
* {@inheritDoc}
6566
*/
6667
@Override
67-
public RemoteAgent start(Launcher launcher, final TaskListener listener) throws Throwable {
68+
public RemoteAgent start(Launcher launcher, final TaskListener listener, FilePath temp) throws Throwable {
69+
// TODO temp directory currently ignored
6870
return launcher.getChannel().call(new MinaRemoteAgentStarter(listener));
6971
}
7072

0 commit comments

Comments
 (0)