How to do remote CVS through multiple SSH connections












2















I know how to use a remote CVS repository where access to the remote server is through SSH.



Here's my problem: the remote CVS server, call it "A" is accessible by SSH only from computers within the same subnet. There is one computer "B" on the subnet that has SSH open to the world. (Don't ask why; I'm not the administrator.) I can SSH into "B", and then from there SSH into "A" where the CVS repository is.



My home PC is not on the same subnet as "A" and "B". Is it possible to access the CVS repository on "A" through my SSH connections between my home PC and "B" and between "B" and "A"?




  • Without hosting another CVS repository on "B".

  • And without checking out on "B" and synchronizing my home PC with that check out.










share|improve this question





























    2















    I know how to use a remote CVS repository where access to the remote server is through SSH.



    Here's my problem: the remote CVS server, call it "A" is accessible by SSH only from computers within the same subnet. There is one computer "B" on the subnet that has SSH open to the world. (Don't ask why; I'm not the administrator.) I can SSH into "B", and then from there SSH into "A" where the CVS repository is.



    My home PC is not on the same subnet as "A" and "B". Is it possible to access the CVS repository on "A" through my SSH connections between my home PC and "B" and between "B" and "A"?




    • Without hosting another CVS repository on "B".

    • And without checking out on "B" and synchronizing my home PC with that check out.










    share|improve this question



























      2












      2








      2








      I know how to use a remote CVS repository where access to the remote server is through SSH.



      Here's my problem: the remote CVS server, call it "A" is accessible by SSH only from computers within the same subnet. There is one computer "B" on the subnet that has SSH open to the world. (Don't ask why; I'm not the administrator.) I can SSH into "B", and then from there SSH into "A" where the CVS repository is.



      My home PC is not on the same subnet as "A" and "B". Is it possible to access the CVS repository on "A" through my SSH connections between my home PC and "B" and between "B" and "A"?




      • Without hosting another CVS repository on "B".

      • And without checking out on "B" and synchronizing my home PC with that check out.










      share|improve this question
















      I know how to use a remote CVS repository where access to the remote server is through SSH.



      Here's my problem: the remote CVS server, call it "A" is accessible by SSH only from computers within the same subnet. There is one computer "B" on the subnet that has SSH open to the world. (Don't ask why; I'm not the administrator.) I can SSH into "B", and then from there SSH into "A" where the CVS repository is.



      My home PC is not on the same subnet as "A" and "B". Is it possible to access the CVS repository on "A" through my SSH connections between my home PC and "B" and between "B" and "A"?




      • Without hosting another CVS repository on "B".

      • And without checking out on "B" and synchronizing my home PC with that check out.







      ssh remote cvs






      share|improve this question















      share|improve this question













      share|improve this question




      share|improve this question








      edited Aug 21 '11 at 7:14









      studiohack

      11.3k1880114




      11.3k1880114










      asked Nov 25 '09 at 6:34









      Posco GrubbPosco Grubb

      4217




      4217






















          3 Answers
          3






          active

          oldest

          votes


















          3














          Quack's answer is a good start, but it has two problems. Thus I'll try it too:



          You first have to create a tunnel from your local workstation to the SSH port of machine A. This is easily done from the command line:



          ssh -L 127.0.0.1:2200:A:22 B


          (ssh to B and create a tunnel from the localport 127.0.0.1:2200 to the remote port A:22)



          Because CVS doesn't allow you to specify ports when using the :ext protocol, this simple command line will not be good enough. What you need to do instead is create or modify your ~/.ssh/config file:



          Host B
          LocalForward 127.0.0.1:2200 A:22

          Host tunnel2a
          Port 2200
          HostName 127.0.0.1


          These are two entries. The first one tells ssh to create a tunnel whenever you ssh to B. The second one defines the new 'hostname' tunnel2a that you can use for cvs.



          First, open the tunnel by ssh'ing to B:



          ssh B


          CVS should now work like that:



          cvs -d :ext:username@tunnel2a:/cvsroot/ checkout someModule





          share|improve this answer





















          • 1





            terrific, manni, thx for the corrections. personally i wouldn't include that host entry for "B"; i'd name it "Btunnel" maybe and point it to "HostName B". that way i'd only get the tunnel on ssh Btunnel and not on every ssh B. otherwise +1.

            – quack quixote
            Nov 25 '09 at 15:46











          • Cool. I didn't know about automatically setting up tunnels through the config file. Thanks.

            – Posco Grubb
            Nov 25 '09 at 17:39



















          1














          You should be able to do this through SSH tunnelling. I don't have 3 machines to test with, but if I understand the process right, you want 2 terminal windows.



          In the first, SSH to "B" with this option: -L 1234:A:22. This will add a tunnel between the localhost, at port 1234, through machine "B", to machine "A", at port 22 (the SSH port).



          The CVS command I originally wrote doesn't work, since CVS doesn't support ports in the :ext: format as I had written. If using a GUI IDE or CVS client, it may allow you to input an alternate port directly. If doing this with the commandline client, you'll need another route -- adding a host alias to your ~/.ssh/config file with the correct port. Manni's answer gives a great example for how that's done, so I won't reproduce that here.



          By aiming at port 1234 on localhost, you'll hit the SSH tunnel and get routed to the SSH port on A.



          You might want to check the answers to some related questions about SSH tunnelling. Thanks Manni for helping me beat these instructions into shape.




          In the second terminal, run your CVS checkout command, but substitute localhost:1234 for A:



          cvs -d :ext:username@localhost:1234:/cvs checkout test
          # instead of
          # cvs -d :ext:username@A:/cvs checkout test







          share|improve this answer


























          • Awesome! Thank you. I had a hunch that tunneling was part of the answer. I don't know if your cvs command is right, but I setup the tunneling and then pointed the CVS client in the Eclipse IDE to use extssh connection to localhost port 1234, and the repositories on "A" showed up. Smooth as butter!

            – Posco Grubb
            Nov 25 '09 at 7:28






          • 1





            This is almost right, but not quite. You don't want the new port on B where it would be accessible to the whole word. You want the port on your local workstation's localhost. ssh -L will do exactly that and thus you need to change the cvs command line because cvs needs to connect to localhost and not to B.

            – innaM
            Nov 25 '09 at 7:36






          • 1





            Oh. And additionally, CVS doesn't allow ports to be specified when using SSH. Duh.

            – innaM
            Nov 25 '09 at 11:01











          • fair points. i'd assume the B->A tunnel wouldn't bypass standard SSH security measures, so it's not horrible. but i said it wrong; my instructions do create the port on the localhost, so B:1234 really should be localhost:1234. oops. (i'll have to take your word for CVS-not-allowing-ports, since I don't use it.)

            – quack quixote
            Nov 25 '09 at 15:33











          • tho i did find lots of messages around the net that mention the same trouble and same solution (cvs-over-ssh via alternate port): see for example lists.freebsd.org/pipermail/freebsd-questions/2006-April/…

            – quack quixote
            Nov 25 '09 at 15:41



















          0














          Having had trouble with innaM's answer, even though it is spot on, and not repeated here, perhaps some additional information could help the odd user having trouble implementing the answer.




          • In the case of difficulty, be sure to experiment with the ssh and cvs commands on the command-line before going to the point of adding the configuration for the LocalForward in the config file. Editing the config file early can be discouraging if anything about a particular setup is slightly different than the answerer's environment.


          • One of the first problems one can encounter is rare, but crucial. It is of paramount importance to know the correct location of the config file. In most cases, the correct location is ~/.ssh/config / ${HOME}/.ssh/config, but, sometimes it is not. The correct config file location is required to solve this problem even when experimenting from a command-line. See also: ssh is no longer using ~/.ssh/config


          • There is also the potential of running afoul of permissions issues. It is usually safe during troubleshooting to set both the .ssh folder and the config file read-only for the user (i.e. chmod 600) though it is not necessarily required that the permissions are quite this tight. In any event, the folder and file should not be writable by other users.



          • There is also the matter of setting CVS_RSH properly. Even if the ssh environment is set up properly, the final cvs command will fail with a very unhelpful message if CVS_RSH is not properly prepared.



            CVS_RSH=ssh; export CVS_RSH


            Without CVS_RSH, the cvs command is likely to return:



            -l: bad option(s)
            cvs [... aborted]: end of file from server (consult above messages if any)



          • It is not necessary to have two shells open to work with the tunnel. innaM's answer says to set up the tunnel with:



            ssh B


            This leaves you with a shell open on B, and not on the local workstation. It is not necessary to have a shell open on B. One can work entirely within a single shell by setting up the tunnel with:



            ssh -fN B


            This command leaves you at the local system prompt rather than at a B prompt. The caveat is that in the case of ssh B it is possible to tear down the forwarding by simply logging off of B, whereas in the case of ssh -fN B the ssh process is in the background and must be killed by other means to tear down the forwarder.



          • When multiple systems require alternate port numbers, adding a Port option to the applicable config Host section is viable.



          • Bear in mind that the config file may specify User in Host sections when user names vary from system to system.



            Another potential pitfall may occur in cases where user names are improperly specified. While it is often correct and proper to specify system user names as user@hostname, DO NOT use this notation in the config file or in the ssh -L parameter. For example, this will go horribly wrong and may be very difficult to unravel:



            ssh -L 2200:Auser@A:22 Buser@B


            (This is never necessary CVS usage since Auser@ is specified with cvs -d :ext:Auser@A:/path/to/repository.)



            While is it perfectly acceptable to specify Buser@B, Auser@ must not be specified this way on either a command-line or in the config file. A cvs command issue with an incorrect command like this may return something like:



            ssh_exchange_identification: read: Connection reset by peer
            cvs [checkout aborted]: end of file from server (consult above messages if any)


            Debugging can be difficult, and can result in other inexplicable messages like:



            SSH Tunnel: channel 3: open failed: administratively prohibited


            The problem is that when used with -L or LocalForward, Auser@ becomes part of the host name (or IP address) so it does not resolve to the expected IP address.








          share|improve this answer

























            Your Answer








            StackExchange.ready(function() {
            var channelOptions = {
            tags: "".split(" "),
            id: "3"
            };
            initTagRenderer("".split(" "), "".split(" "), channelOptions);

            StackExchange.using("externalEditor", function() {
            // Have to fire editor after snippets, if snippets enabled
            if (StackExchange.settings.snippets.snippetsEnabled) {
            StackExchange.using("snippets", function() {
            createEditor();
            });
            }
            else {
            createEditor();
            }
            });

            function createEditor() {
            StackExchange.prepareEditor({
            heartbeatType: 'answer',
            autoActivateHeartbeat: false,
            convertImagesToLinks: true,
            noModals: true,
            showLowRepImageUploadWarning: true,
            reputationToPostImages: 10,
            bindNavPrevention: true,
            postfix: "",
            imageUploader: {
            brandingHtml: "Powered by u003ca class="icon-imgur-white" href="https://imgur.com/"u003eu003c/au003e",
            contentPolicyHtml: "User contributions licensed under u003ca href="https://creativecommons.org/licenses/by-sa/3.0/"u003ecc by-sa 3.0 with attribution requiredu003c/au003e u003ca href="https://stackoverflow.com/legal/content-policy"u003e(content policy)u003c/au003e",
            allowUrls: true
            },
            onDemand: true,
            discardSelector: ".discard-answer"
            ,immediatelyShowMarkdownHelp:true
            });


            }
            });














            draft saved

            draft discarded


















            StackExchange.ready(
            function () {
            StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2fsuperuser.com%2fquestions%2f75080%2fhow-to-do-remote-cvs-through-multiple-ssh-connections%23new-answer', 'question_page');
            }
            );

            Post as a guest















            Required, but never shown

























            3 Answers
            3






            active

            oldest

            votes








            3 Answers
            3






            active

            oldest

            votes









            active

            oldest

            votes






            active

            oldest

            votes









            3














            Quack's answer is a good start, but it has two problems. Thus I'll try it too:



            You first have to create a tunnel from your local workstation to the SSH port of machine A. This is easily done from the command line:



            ssh -L 127.0.0.1:2200:A:22 B


            (ssh to B and create a tunnel from the localport 127.0.0.1:2200 to the remote port A:22)



            Because CVS doesn't allow you to specify ports when using the :ext protocol, this simple command line will not be good enough. What you need to do instead is create or modify your ~/.ssh/config file:



            Host B
            LocalForward 127.0.0.1:2200 A:22

            Host tunnel2a
            Port 2200
            HostName 127.0.0.1


            These are two entries. The first one tells ssh to create a tunnel whenever you ssh to B. The second one defines the new 'hostname' tunnel2a that you can use for cvs.



            First, open the tunnel by ssh'ing to B:



            ssh B


            CVS should now work like that:



            cvs -d :ext:username@tunnel2a:/cvsroot/ checkout someModule





            share|improve this answer





















            • 1





              terrific, manni, thx for the corrections. personally i wouldn't include that host entry for "B"; i'd name it "Btunnel" maybe and point it to "HostName B". that way i'd only get the tunnel on ssh Btunnel and not on every ssh B. otherwise +1.

              – quack quixote
              Nov 25 '09 at 15:46











            • Cool. I didn't know about automatically setting up tunnels through the config file. Thanks.

              – Posco Grubb
              Nov 25 '09 at 17:39
















            3














            Quack's answer is a good start, but it has two problems. Thus I'll try it too:



            You first have to create a tunnel from your local workstation to the SSH port of machine A. This is easily done from the command line:



            ssh -L 127.0.0.1:2200:A:22 B


            (ssh to B and create a tunnel from the localport 127.0.0.1:2200 to the remote port A:22)



            Because CVS doesn't allow you to specify ports when using the :ext protocol, this simple command line will not be good enough. What you need to do instead is create or modify your ~/.ssh/config file:



            Host B
            LocalForward 127.0.0.1:2200 A:22

            Host tunnel2a
            Port 2200
            HostName 127.0.0.1


            These are two entries. The first one tells ssh to create a tunnel whenever you ssh to B. The second one defines the new 'hostname' tunnel2a that you can use for cvs.



            First, open the tunnel by ssh'ing to B:



            ssh B


            CVS should now work like that:



            cvs -d :ext:username@tunnel2a:/cvsroot/ checkout someModule





            share|improve this answer





















            • 1





              terrific, manni, thx for the corrections. personally i wouldn't include that host entry for "B"; i'd name it "Btunnel" maybe and point it to "HostName B". that way i'd only get the tunnel on ssh Btunnel and not on every ssh B. otherwise +1.

              – quack quixote
              Nov 25 '09 at 15:46











            • Cool. I didn't know about automatically setting up tunnels through the config file. Thanks.

              – Posco Grubb
              Nov 25 '09 at 17:39














            3












            3








            3







            Quack's answer is a good start, but it has two problems. Thus I'll try it too:



            You first have to create a tunnel from your local workstation to the SSH port of machine A. This is easily done from the command line:



            ssh -L 127.0.0.1:2200:A:22 B


            (ssh to B and create a tunnel from the localport 127.0.0.1:2200 to the remote port A:22)



            Because CVS doesn't allow you to specify ports when using the :ext protocol, this simple command line will not be good enough. What you need to do instead is create or modify your ~/.ssh/config file:



            Host B
            LocalForward 127.0.0.1:2200 A:22

            Host tunnel2a
            Port 2200
            HostName 127.0.0.1


            These are two entries. The first one tells ssh to create a tunnel whenever you ssh to B. The second one defines the new 'hostname' tunnel2a that you can use for cvs.



            First, open the tunnel by ssh'ing to B:



            ssh B


            CVS should now work like that:



            cvs -d :ext:username@tunnel2a:/cvsroot/ checkout someModule





            share|improve this answer















            Quack's answer is a good start, but it has two problems. Thus I'll try it too:



            You first have to create a tunnel from your local workstation to the SSH port of machine A. This is easily done from the command line:



            ssh -L 127.0.0.1:2200:A:22 B


            (ssh to B and create a tunnel from the localport 127.0.0.1:2200 to the remote port A:22)



            Because CVS doesn't allow you to specify ports when using the :ext protocol, this simple command line will not be good enough. What you need to do instead is create or modify your ~/.ssh/config file:



            Host B
            LocalForward 127.0.0.1:2200 A:22

            Host tunnel2a
            Port 2200
            HostName 127.0.0.1


            These are two entries. The first one tells ssh to create a tunnel whenever you ssh to B. The second one defines the new 'hostname' tunnel2a that you can use for cvs.



            First, open the tunnel by ssh'ing to B:



            ssh B


            CVS should now work like that:



            cvs -d :ext:username@tunnel2a:/cvsroot/ checkout someModule






            share|improve this answer














            share|improve this answer



            share|improve this answer








            edited Nov 25 '09 at 11:27

























            answered Nov 25 '09 at 11:10









            innaMinnaM

            7,96833248




            7,96833248








            • 1





              terrific, manni, thx for the corrections. personally i wouldn't include that host entry for "B"; i'd name it "Btunnel" maybe and point it to "HostName B". that way i'd only get the tunnel on ssh Btunnel and not on every ssh B. otherwise +1.

              – quack quixote
              Nov 25 '09 at 15:46











            • Cool. I didn't know about automatically setting up tunnels through the config file. Thanks.

              – Posco Grubb
              Nov 25 '09 at 17:39














            • 1





              terrific, manni, thx for the corrections. personally i wouldn't include that host entry for "B"; i'd name it "Btunnel" maybe and point it to "HostName B". that way i'd only get the tunnel on ssh Btunnel and not on every ssh B. otherwise +1.

              – quack quixote
              Nov 25 '09 at 15:46











            • Cool. I didn't know about automatically setting up tunnels through the config file. Thanks.

              – Posco Grubb
              Nov 25 '09 at 17:39








            1




            1





            terrific, manni, thx for the corrections. personally i wouldn't include that host entry for "B"; i'd name it "Btunnel" maybe and point it to "HostName B". that way i'd only get the tunnel on ssh Btunnel and not on every ssh B. otherwise +1.

            – quack quixote
            Nov 25 '09 at 15:46





            terrific, manni, thx for the corrections. personally i wouldn't include that host entry for "B"; i'd name it "Btunnel" maybe and point it to "HostName B". that way i'd only get the tunnel on ssh Btunnel and not on every ssh B. otherwise +1.

            – quack quixote
            Nov 25 '09 at 15:46













            Cool. I didn't know about automatically setting up tunnels through the config file. Thanks.

            – Posco Grubb
            Nov 25 '09 at 17:39





            Cool. I didn't know about automatically setting up tunnels through the config file. Thanks.

            – Posco Grubb
            Nov 25 '09 at 17:39













            1














            You should be able to do this through SSH tunnelling. I don't have 3 machines to test with, but if I understand the process right, you want 2 terminal windows.



            In the first, SSH to "B" with this option: -L 1234:A:22. This will add a tunnel between the localhost, at port 1234, through machine "B", to machine "A", at port 22 (the SSH port).



            The CVS command I originally wrote doesn't work, since CVS doesn't support ports in the :ext: format as I had written. If using a GUI IDE or CVS client, it may allow you to input an alternate port directly. If doing this with the commandline client, you'll need another route -- adding a host alias to your ~/.ssh/config file with the correct port. Manni's answer gives a great example for how that's done, so I won't reproduce that here.



            By aiming at port 1234 on localhost, you'll hit the SSH tunnel and get routed to the SSH port on A.



            You might want to check the answers to some related questions about SSH tunnelling. Thanks Manni for helping me beat these instructions into shape.




            In the second terminal, run your CVS checkout command, but substitute localhost:1234 for A:



            cvs -d :ext:username@localhost:1234:/cvs checkout test
            # instead of
            # cvs -d :ext:username@A:/cvs checkout test







            share|improve this answer


























            • Awesome! Thank you. I had a hunch that tunneling was part of the answer. I don't know if your cvs command is right, but I setup the tunneling and then pointed the CVS client in the Eclipse IDE to use extssh connection to localhost port 1234, and the repositories on "A" showed up. Smooth as butter!

              – Posco Grubb
              Nov 25 '09 at 7:28






            • 1





              This is almost right, but not quite. You don't want the new port on B where it would be accessible to the whole word. You want the port on your local workstation's localhost. ssh -L will do exactly that and thus you need to change the cvs command line because cvs needs to connect to localhost and not to B.

              – innaM
              Nov 25 '09 at 7:36






            • 1





              Oh. And additionally, CVS doesn't allow ports to be specified when using SSH. Duh.

              – innaM
              Nov 25 '09 at 11:01











            • fair points. i'd assume the B->A tunnel wouldn't bypass standard SSH security measures, so it's not horrible. but i said it wrong; my instructions do create the port on the localhost, so B:1234 really should be localhost:1234. oops. (i'll have to take your word for CVS-not-allowing-ports, since I don't use it.)

              – quack quixote
              Nov 25 '09 at 15:33











            • tho i did find lots of messages around the net that mention the same trouble and same solution (cvs-over-ssh via alternate port): see for example lists.freebsd.org/pipermail/freebsd-questions/2006-April/…

              – quack quixote
              Nov 25 '09 at 15:41
















            1














            You should be able to do this through SSH tunnelling. I don't have 3 machines to test with, but if I understand the process right, you want 2 terminal windows.



            In the first, SSH to "B" with this option: -L 1234:A:22. This will add a tunnel between the localhost, at port 1234, through machine "B", to machine "A", at port 22 (the SSH port).



            The CVS command I originally wrote doesn't work, since CVS doesn't support ports in the :ext: format as I had written. If using a GUI IDE or CVS client, it may allow you to input an alternate port directly. If doing this with the commandline client, you'll need another route -- adding a host alias to your ~/.ssh/config file with the correct port. Manni's answer gives a great example for how that's done, so I won't reproduce that here.



            By aiming at port 1234 on localhost, you'll hit the SSH tunnel and get routed to the SSH port on A.



            You might want to check the answers to some related questions about SSH tunnelling. Thanks Manni for helping me beat these instructions into shape.




            In the second terminal, run your CVS checkout command, but substitute localhost:1234 for A:



            cvs -d :ext:username@localhost:1234:/cvs checkout test
            # instead of
            # cvs -d :ext:username@A:/cvs checkout test







            share|improve this answer


























            • Awesome! Thank you. I had a hunch that tunneling was part of the answer. I don't know if your cvs command is right, but I setup the tunneling and then pointed the CVS client in the Eclipse IDE to use extssh connection to localhost port 1234, and the repositories on "A" showed up. Smooth as butter!

              – Posco Grubb
              Nov 25 '09 at 7:28






            • 1





              This is almost right, but not quite. You don't want the new port on B where it would be accessible to the whole word. You want the port on your local workstation's localhost. ssh -L will do exactly that and thus you need to change the cvs command line because cvs needs to connect to localhost and not to B.

              – innaM
              Nov 25 '09 at 7:36






            • 1





              Oh. And additionally, CVS doesn't allow ports to be specified when using SSH. Duh.

              – innaM
              Nov 25 '09 at 11:01











            • fair points. i'd assume the B->A tunnel wouldn't bypass standard SSH security measures, so it's not horrible. but i said it wrong; my instructions do create the port on the localhost, so B:1234 really should be localhost:1234. oops. (i'll have to take your word for CVS-not-allowing-ports, since I don't use it.)

              – quack quixote
              Nov 25 '09 at 15:33











            • tho i did find lots of messages around the net that mention the same trouble and same solution (cvs-over-ssh via alternate port): see for example lists.freebsd.org/pipermail/freebsd-questions/2006-April/…

              – quack quixote
              Nov 25 '09 at 15:41














            1












            1








            1







            You should be able to do this through SSH tunnelling. I don't have 3 machines to test with, but if I understand the process right, you want 2 terminal windows.



            In the first, SSH to "B" with this option: -L 1234:A:22. This will add a tunnel between the localhost, at port 1234, through machine "B", to machine "A", at port 22 (the SSH port).



            The CVS command I originally wrote doesn't work, since CVS doesn't support ports in the :ext: format as I had written. If using a GUI IDE or CVS client, it may allow you to input an alternate port directly. If doing this with the commandline client, you'll need another route -- adding a host alias to your ~/.ssh/config file with the correct port. Manni's answer gives a great example for how that's done, so I won't reproduce that here.



            By aiming at port 1234 on localhost, you'll hit the SSH tunnel and get routed to the SSH port on A.



            You might want to check the answers to some related questions about SSH tunnelling. Thanks Manni for helping me beat these instructions into shape.




            In the second terminal, run your CVS checkout command, but substitute localhost:1234 for A:



            cvs -d :ext:username@localhost:1234:/cvs checkout test
            # instead of
            # cvs -d :ext:username@A:/cvs checkout test







            share|improve this answer















            You should be able to do this through SSH tunnelling. I don't have 3 machines to test with, but if I understand the process right, you want 2 terminal windows.



            In the first, SSH to "B" with this option: -L 1234:A:22. This will add a tunnel between the localhost, at port 1234, through machine "B", to machine "A", at port 22 (the SSH port).



            The CVS command I originally wrote doesn't work, since CVS doesn't support ports in the :ext: format as I had written. If using a GUI IDE or CVS client, it may allow you to input an alternate port directly. If doing this with the commandline client, you'll need another route -- adding a host alias to your ~/.ssh/config file with the correct port. Manni's answer gives a great example for how that's done, so I won't reproduce that here.



            By aiming at port 1234 on localhost, you'll hit the SSH tunnel and get routed to the SSH port on A.



            You might want to check the answers to some related questions about SSH tunnelling. Thanks Manni for helping me beat these instructions into shape.




            In the second terminal, run your CVS checkout command, but substitute localhost:1234 for A:



            cvs -d :ext:username@localhost:1234:/cvs checkout test
            # instead of
            # cvs -d :ext:username@A:/cvs checkout test








            share|improve this answer














            share|improve this answer



            share|improve this answer








            edited Mar 20 '17 at 10:17









            Community

            1




            1










            answered Nov 25 '09 at 6:58









            quack quixotequack quixote

            35.3k1087119




            35.3k1087119













            • Awesome! Thank you. I had a hunch that tunneling was part of the answer. I don't know if your cvs command is right, but I setup the tunneling and then pointed the CVS client in the Eclipse IDE to use extssh connection to localhost port 1234, and the repositories on "A" showed up. Smooth as butter!

              – Posco Grubb
              Nov 25 '09 at 7:28






            • 1





              This is almost right, but not quite. You don't want the new port on B where it would be accessible to the whole word. You want the port on your local workstation's localhost. ssh -L will do exactly that and thus you need to change the cvs command line because cvs needs to connect to localhost and not to B.

              – innaM
              Nov 25 '09 at 7:36






            • 1





              Oh. And additionally, CVS doesn't allow ports to be specified when using SSH. Duh.

              – innaM
              Nov 25 '09 at 11:01











            • fair points. i'd assume the B->A tunnel wouldn't bypass standard SSH security measures, so it's not horrible. but i said it wrong; my instructions do create the port on the localhost, so B:1234 really should be localhost:1234. oops. (i'll have to take your word for CVS-not-allowing-ports, since I don't use it.)

              – quack quixote
              Nov 25 '09 at 15:33











            • tho i did find lots of messages around the net that mention the same trouble and same solution (cvs-over-ssh via alternate port): see for example lists.freebsd.org/pipermail/freebsd-questions/2006-April/…

              – quack quixote
              Nov 25 '09 at 15:41



















            • Awesome! Thank you. I had a hunch that tunneling was part of the answer. I don't know if your cvs command is right, but I setup the tunneling and then pointed the CVS client in the Eclipse IDE to use extssh connection to localhost port 1234, and the repositories on "A" showed up. Smooth as butter!

              – Posco Grubb
              Nov 25 '09 at 7:28






            • 1





              This is almost right, but not quite. You don't want the new port on B where it would be accessible to the whole word. You want the port on your local workstation's localhost. ssh -L will do exactly that and thus you need to change the cvs command line because cvs needs to connect to localhost and not to B.

              – innaM
              Nov 25 '09 at 7:36






            • 1





              Oh. And additionally, CVS doesn't allow ports to be specified when using SSH. Duh.

              – innaM
              Nov 25 '09 at 11:01











            • fair points. i'd assume the B->A tunnel wouldn't bypass standard SSH security measures, so it's not horrible. but i said it wrong; my instructions do create the port on the localhost, so B:1234 really should be localhost:1234. oops. (i'll have to take your word for CVS-not-allowing-ports, since I don't use it.)

              – quack quixote
              Nov 25 '09 at 15:33











            • tho i did find lots of messages around the net that mention the same trouble and same solution (cvs-over-ssh via alternate port): see for example lists.freebsd.org/pipermail/freebsd-questions/2006-April/…

              – quack quixote
              Nov 25 '09 at 15:41

















            Awesome! Thank you. I had a hunch that tunneling was part of the answer. I don't know if your cvs command is right, but I setup the tunneling and then pointed the CVS client in the Eclipse IDE to use extssh connection to localhost port 1234, and the repositories on "A" showed up. Smooth as butter!

            – Posco Grubb
            Nov 25 '09 at 7:28





            Awesome! Thank you. I had a hunch that tunneling was part of the answer. I don't know if your cvs command is right, but I setup the tunneling and then pointed the CVS client in the Eclipse IDE to use extssh connection to localhost port 1234, and the repositories on "A" showed up. Smooth as butter!

            – Posco Grubb
            Nov 25 '09 at 7:28




            1




            1





            This is almost right, but not quite. You don't want the new port on B where it would be accessible to the whole word. You want the port on your local workstation's localhost. ssh -L will do exactly that and thus you need to change the cvs command line because cvs needs to connect to localhost and not to B.

            – innaM
            Nov 25 '09 at 7:36





            This is almost right, but not quite. You don't want the new port on B where it would be accessible to the whole word. You want the port on your local workstation's localhost. ssh -L will do exactly that and thus you need to change the cvs command line because cvs needs to connect to localhost and not to B.

            – innaM
            Nov 25 '09 at 7:36




            1




            1





            Oh. And additionally, CVS doesn't allow ports to be specified when using SSH. Duh.

            – innaM
            Nov 25 '09 at 11:01





            Oh. And additionally, CVS doesn't allow ports to be specified when using SSH. Duh.

            – innaM
            Nov 25 '09 at 11:01













            fair points. i'd assume the B->A tunnel wouldn't bypass standard SSH security measures, so it's not horrible. but i said it wrong; my instructions do create the port on the localhost, so B:1234 really should be localhost:1234. oops. (i'll have to take your word for CVS-not-allowing-ports, since I don't use it.)

            – quack quixote
            Nov 25 '09 at 15:33





            fair points. i'd assume the B->A tunnel wouldn't bypass standard SSH security measures, so it's not horrible. but i said it wrong; my instructions do create the port on the localhost, so B:1234 really should be localhost:1234. oops. (i'll have to take your word for CVS-not-allowing-ports, since I don't use it.)

            – quack quixote
            Nov 25 '09 at 15:33













            tho i did find lots of messages around the net that mention the same trouble and same solution (cvs-over-ssh via alternate port): see for example lists.freebsd.org/pipermail/freebsd-questions/2006-April/…

            – quack quixote
            Nov 25 '09 at 15:41





            tho i did find lots of messages around the net that mention the same trouble and same solution (cvs-over-ssh via alternate port): see for example lists.freebsd.org/pipermail/freebsd-questions/2006-April/…

            – quack quixote
            Nov 25 '09 at 15:41











            0














            Having had trouble with innaM's answer, even though it is spot on, and not repeated here, perhaps some additional information could help the odd user having trouble implementing the answer.




            • In the case of difficulty, be sure to experiment with the ssh and cvs commands on the command-line before going to the point of adding the configuration for the LocalForward in the config file. Editing the config file early can be discouraging if anything about a particular setup is slightly different than the answerer's environment.


            • One of the first problems one can encounter is rare, but crucial. It is of paramount importance to know the correct location of the config file. In most cases, the correct location is ~/.ssh/config / ${HOME}/.ssh/config, but, sometimes it is not. The correct config file location is required to solve this problem even when experimenting from a command-line. See also: ssh is no longer using ~/.ssh/config


            • There is also the potential of running afoul of permissions issues. It is usually safe during troubleshooting to set both the .ssh folder and the config file read-only for the user (i.e. chmod 600) though it is not necessarily required that the permissions are quite this tight. In any event, the folder and file should not be writable by other users.



            • There is also the matter of setting CVS_RSH properly. Even if the ssh environment is set up properly, the final cvs command will fail with a very unhelpful message if CVS_RSH is not properly prepared.



              CVS_RSH=ssh; export CVS_RSH


              Without CVS_RSH, the cvs command is likely to return:



              -l: bad option(s)
              cvs [... aborted]: end of file from server (consult above messages if any)



            • It is not necessary to have two shells open to work with the tunnel. innaM's answer says to set up the tunnel with:



              ssh B


              This leaves you with a shell open on B, and not on the local workstation. It is not necessary to have a shell open on B. One can work entirely within a single shell by setting up the tunnel with:



              ssh -fN B


              This command leaves you at the local system prompt rather than at a B prompt. The caveat is that in the case of ssh B it is possible to tear down the forwarding by simply logging off of B, whereas in the case of ssh -fN B the ssh process is in the background and must be killed by other means to tear down the forwarder.



            • When multiple systems require alternate port numbers, adding a Port option to the applicable config Host section is viable.



            • Bear in mind that the config file may specify User in Host sections when user names vary from system to system.



              Another potential pitfall may occur in cases where user names are improperly specified. While it is often correct and proper to specify system user names as user@hostname, DO NOT use this notation in the config file or in the ssh -L parameter. For example, this will go horribly wrong and may be very difficult to unravel:



              ssh -L 2200:Auser@A:22 Buser@B


              (This is never necessary CVS usage since Auser@ is specified with cvs -d :ext:Auser@A:/path/to/repository.)



              While is it perfectly acceptable to specify Buser@B, Auser@ must not be specified this way on either a command-line or in the config file. A cvs command issue with an incorrect command like this may return something like:



              ssh_exchange_identification: read: Connection reset by peer
              cvs [checkout aborted]: end of file from server (consult above messages if any)


              Debugging can be difficult, and can result in other inexplicable messages like:



              SSH Tunnel: channel 3: open failed: administratively prohibited


              The problem is that when used with -L or LocalForward, Auser@ becomes part of the host name (or IP address) so it does not resolve to the expected IP address.








            share|improve this answer






























              0














              Having had trouble with innaM's answer, even though it is spot on, and not repeated here, perhaps some additional information could help the odd user having trouble implementing the answer.




              • In the case of difficulty, be sure to experiment with the ssh and cvs commands on the command-line before going to the point of adding the configuration for the LocalForward in the config file. Editing the config file early can be discouraging if anything about a particular setup is slightly different than the answerer's environment.


              • One of the first problems one can encounter is rare, but crucial. It is of paramount importance to know the correct location of the config file. In most cases, the correct location is ~/.ssh/config / ${HOME}/.ssh/config, but, sometimes it is not. The correct config file location is required to solve this problem even when experimenting from a command-line. See also: ssh is no longer using ~/.ssh/config


              • There is also the potential of running afoul of permissions issues. It is usually safe during troubleshooting to set both the .ssh folder and the config file read-only for the user (i.e. chmod 600) though it is not necessarily required that the permissions are quite this tight. In any event, the folder and file should not be writable by other users.



              • There is also the matter of setting CVS_RSH properly. Even if the ssh environment is set up properly, the final cvs command will fail with a very unhelpful message if CVS_RSH is not properly prepared.



                CVS_RSH=ssh; export CVS_RSH


                Without CVS_RSH, the cvs command is likely to return:



                -l: bad option(s)
                cvs [... aborted]: end of file from server (consult above messages if any)



              • It is not necessary to have two shells open to work with the tunnel. innaM's answer says to set up the tunnel with:



                ssh B


                This leaves you with a shell open on B, and not on the local workstation. It is not necessary to have a shell open on B. One can work entirely within a single shell by setting up the tunnel with:



                ssh -fN B


                This command leaves you at the local system prompt rather than at a B prompt. The caveat is that in the case of ssh B it is possible to tear down the forwarding by simply logging off of B, whereas in the case of ssh -fN B the ssh process is in the background and must be killed by other means to tear down the forwarder.



              • When multiple systems require alternate port numbers, adding a Port option to the applicable config Host section is viable.



              • Bear in mind that the config file may specify User in Host sections when user names vary from system to system.



                Another potential pitfall may occur in cases where user names are improperly specified. While it is often correct and proper to specify system user names as user@hostname, DO NOT use this notation in the config file or in the ssh -L parameter. For example, this will go horribly wrong and may be very difficult to unravel:



                ssh -L 2200:Auser@A:22 Buser@B


                (This is never necessary CVS usage since Auser@ is specified with cvs -d :ext:Auser@A:/path/to/repository.)



                While is it perfectly acceptable to specify Buser@B, Auser@ must not be specified this way on either a command-line or in the config file. A cvs command issue with an incorrect command like this may return something like:



                ssh_exchange_identification: read: Connection reset by peer
                cvs [checkout aborted]: end of file from server (consult above messages if any)


                Debugging can be difficult, and can result in other inexplicable messages like:



                SSH Tunnel: channel 3: open failed: administratively prohibited


                The problem is that when used with -L or LocalForward, Auser@ becomes part of the host name (or IP address) so it does not resolve to the expected IP address.








              share|improve this answer




























                0












                0








                0







                Having had trouble with innaM's answer, even though it is spot on, and not repeated here, perhaps some additional information could help the odd user having trouble implementing the answer.




                • In the case of difficulty, be sure to experiment with the ssh and cvs commands on the command-line before going to the point of adding the configuration for the LocalForward in the config file. Editing the config file early can be discouraging if anything about a particular setup is slightly different than the answerer's environment.


                • One of the first problems one can encounter is rare, but crucial. It is of paramount importance to know the correct location of the config file. In most cases, the correct location is ~/.ssh/config / ${HOME}/.ssh/config, but, sometimes it is not. The correct config file location is required to solve this problem even when experimenting from a command-line. See also: ssh is no longer using ~/.ssh/config


                • There is also the potential of running afoul of permissions issues. It is usually safe during troubleshooting to set both the .ssh folder and the config file read-only for the user (i.e. chmod 600) though it is not necessarily required that the permissions are quite this tight. In any event, the folder and file should not be writable by other users.



                • There is also the matter of setting CVS_RSH properly. Even if the ssh environment is set up properly, the final cvs command will fail with a very unhelpful message if CVS_RSH is not properly prepared.



                  CVS_RSH=ssh; export CVS_RSH


                  Without CVS_RSH, the cvs command is likely to return:



                  -l: bad option(s)
                  cvs [... aborted]: end of file from server (consult above messages if any)



                • It is not necessary to have two shells open to work with the tunnel. innaM's answer says to set up the tunnel with:



                  ssh B


                  This leaves you with a shell open on B, and not on the local workstation. It is not necessary to have a shell open on B. One can work entirely within a single shell by setting up the tunnel with:



                  ssh -fN B


                  This command leaves you at the local system prompt rather than at a B prompt. The caveat is that in the case of ssh B it is possible to tear down the forwarding by simply logging off of B, whereas in the case of ssh -fN B the ssh process is in the background and must be killed by other means to tear down the forwarder.



                • When multiple systems require alternate port numbers, adding a Port option to the applicable config Host section is viable.



                • Bear in mind that the config file may specify User in Host sections when user names vary from system to system.



                  Another potential pitfall may occur in cases where user names are improperly specified. While it is often correct and proper to specify system user names as user@hostname, DO NOT use this notation in the config file or in the ssh -L parameter. For example, this will go horribly wrong and may be very difficult to unravel:



                  ssh -L 2200:Auser@A:22 Buser@B


                  (This is never necessary CVS usage since Auser@ is specified with cvs -d :ext:Auser@A:/path/to/repository.)



                  While is it perfectly acceptable to specify Buser@B, Auser@ must not be specified this way on either a command-line or in the config file. A cvs command issue with an incorrect command like this may return something like:



                  ssh_exchange_identification: read: Connection reset by peer
                  cvs [checkout aborted]: end of file from server (consult above messages if any)


                  Debugging can be difficult, and can result in other inexplicable messages like:



                  SSH Tunnel: channel 3: open failed: administratively prohibited


                  The problem is that when used with -L or LocalForward, Auser@ becomes part of the host name (or IP address) so it does not resolve to the expected IP address.








                share|improve this answer















                Having had trouble with innaM's answer, even though it is spot on, and not repeated here, perhaps some additional information could help the odd user having trouble implementing the answer.




                • In the case of difficulty, be sure to experiment with the ssh and cvs commands on the command-line before going to the point of adding the configuration for the LocalForward in the config file. Editing the config file early can be discouraging if anything about a particular setup is slightly different than the answerer's environment.


                • One of the first problems one can encounter is rare, but crucial. It is of paramount importance to know the correct location of the config file. In most cases, the correct location is ~/.ssh/config / ${HOME}/.ssh/config, but, sometimes it is not. The correct config file location is required to solve this problem even when experimenting from a command-line. See also: ssh is no longer using ~/.ssh/config


                • There is also the potential of running afoul of permissions issues. It is usually safe during troubleshooting to set both the .ssh folder and the config file read-only for the user (i.e. chmod 600) though it is not necessarily required that the permissions are quite this tight. In any event, the folder and file should not be writable by other users.



                • There is also the matter of setting CVS_RSH properly. Even if the ssh environment is set up properly, the final cvs command will fail with a very unhelpful message if CVS_RSH is not properly prepared.



                  CVS_RSH=ssh; export CVS_RSH


                  Without CVS_RSH, the cvs command is likely to return:



                  -l: bad option(s)
                  cvs [... aborted]: end of file from server (consult above messages if any)



                • It is not necessary to have two shells open to work with the tunnel. innaM's answer says to set up the tunnel with:



                  ssh B


                  This leaves you with a shell open on B, and not on the local workstation. It is not necessary to have a shell open on B. One can work entirely within a single shell by setting up the tunnel with:



                  ssh -fN B


                  This command leaves you at the local system prompt rather than at a B prompt. The caveat is that in the case of ssh B it is possible to tear down the forwarding by simply logging off of B, whereas in the case of ssh -fN B the ssh process is in the background and must be killed by other means to tear down the forwarder.



                • When multiple systems require alternate port numbers, adding a Port option to the applicable config Host section is viable.



                • Bear in mind that the config file may specify User in Host sections when user names vary from system to system.



                  Another potential pitfall may occur in cases where user names are improperly specified. While it is often correct and proper to specify system user names as user@hostname, DO NOT use this notation in the config file or in the ssh -L parameter. For example, this will go horribly wrong and may be very difficult to unravel:



                  ssh -L 2200:Auser@A:22 Buser@B


                  (This is never necessary CVS usage since Auser@ is specified with cvs -d :ext:Auser@A:/path/to/repository.)



                  While is it perfectly acceptable to specify Buser@B, Auser@ must not be specified this way on either a command-line or in the config file. A cvs command issue with an incorrect command like this may return something like:



                  ssh_exchange_identification: read: Connection reset by peer
                  cvs [checkout aborted]: end of file from server (consult above messages if any)


                  Debugging can be difficult, and can result in other inexplicable messages like:



                  SSH Tunnel: channel 3: open failed: administratively prohibited


                  The problem is that when used with -L or LocalForward, Auser@ becomes part of the host name (or IP address) so it does not resolve to the expected IP address.









                share|improve this answer














                share|improve this answer



                share|improve this answer








                edited Feb 1 at 21:54

























                answered Feb 1 at 21:44









                kbulgrienkbulgrien

                290411




                290411






























                    draft saved

                    draft discarded




















































                    Thanks for contributing an answer to Super User!


                    • Please be sure to answer the question. Provide details and share your research!

                    But avoid



                    • Asking for help, clarification, or responding to other answers.

                    • Making statements based on opinion; back them up with references or personal experience.


                    To learn more, see our tips on writing great answers.




                    draft saved


                    draft discarded














                    StackExchange.ready(
                    function () {
                    StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2fsuperuser.com%2fquestions%2f75080%2fhow-to-do-remote-cvs-through-multiple-ssh-connections%23new-answer', 'question_page');
                    }
                    );

                    Post as a guest















                    Required, but never shown





















































                    Required, but never shown














                    Required, but never shown












                    Required, but never shown







                    Required, but never shown

































                    Required, but never shown














                    Required, but never shown












                    Required, but never shown







                    Required, but never shown







                    Popular posts from this blog

                    flock() on closed filehandle LOCK_FILE at /usr/bin/apt-mirror

                    Mangá

                     ⁒  ․,‪⁊‑⁙ ⁖, ⁇‒※‌, †,⁖‗‌⁝    ‾‸⁘,‖⁔⁣,⁂‾
”‑,‥–,‬ ,⁀‹⁋‴⁑ ‒ ,‴⁋”‼ ⁨,‷⁔„ ‰′,‐‚ ‥‡‎“‷⁃⁨⁅⁣,⁔
⁇‘⁔⁡⁏⁌⁡‿‶‏⁨ ⁣⁕⁖⁨⁩⁥‽⁀  ‴‬⁜‟ ⁃‣‧⁕‮ …‍⁨‴ ⁩,⁚⁖‫ ,‵ ⁀,‮⁝‣‣ ⁑  ⁂– ․, ‾‽ ‏⁁“⁗‸ ‾… ‹‡⁌⁎‸‘ ‡⁏⁌‪ ‵⁛ ‎⁨ ―⁦⁤⁄⁕