Original post

Hi all,

I’m making a tool, that can check a CIDR and see if a domain belongs to one server in the CIDR.
I wanted to do it similar as I do with cUrl, doing the request to the ip address, for example: http://1.2.3.4 and setting the Host Header: example.com

So far the code I have is always returning Status Code 200, but the host exist just in one of the IP I have set. Why is this behavior and how can I get the right behavior from my http request?

Here is the code

package main

import (
        "fmt"
        "log"
        "net"
        "net/http"
        "time"
)

func main() {

        var domain = "anillodegrado.com.ve"

        fmt.Println("Analyzing Domain: ", domain)

        ipAddresses, err := Hosts("198.50.181.32/27")
        if err != nil {
                log.Fatal(err)
        }

        for _, ips := range ipAddresses {
                req, err := http.NewRequest("GET", "http://"+ips, nil)
                if err != nil {
                        log.Fatal("Error reading request. ", err)
                }

                fmt.Println("Using IP: ", ips)

                req.Host = domain
                req.URL.Host = domain
                //req.Header.Set("Host", domain)

                client := &http.Client{Timeout: time.Second * 10}

                resp, err := client.Do(req)
                if err != nil {
                        log.Fatal("Error reading response. ", err)
                }
                defer resp.Body.Close()

                //body, err := ioutil.ReadAll(resp.Body)
                //if err != nil {
                //      log.Fatal("Error reading body", err)
                //}

                fmt.Println("HTTP Status: ", resp.StatusCode)
                fmt.Println("Content Length: ", resp.ContentLength)
                //log.Println(string(body))
        }
}

// Hosts function read a CIDR and create a slide with all the IP addresses contained in it
func Hosts(cidr string) ([]string, error) {
        ip, ipnet, err := net.ParseCIDR(cidr)
        if err != nil {
                return nil, err
        }

        var ips []string
        for ip := ip.Mask(ipnet.Mask); ipnet.Contains(ip); inc(ip) {
                ips = append(ips, ip.String())
        }

        // remove network address and broadcast address
        lenIPs := len(ips)
        switch {
        case lenIPs < 2:
                return ips, nil

        default:
                return ips[1 : len(ips)-1], nil
        }
}

func inc(ip net.IP) {
        for j := len(ip) - 1; j >= 0; j-- {
                ip[j]++
                if ip[j] > 0 {
                        break
                }
        }
}

Thanks in advance

I tried this example https://stackoverflow.com/questions/40624248/golang-force-http-request-to-specific-ip-similar-to-curl-resolve , but the result is the same

You set the request.URL.Host to the same hostname every time and not just the request http header. You are basically changing the url on the request made for the IP address.

Also, you should check if resp.Body is nil before calling Close on it :slight_smile:

Hey, You can use below code to get IP from HTTP req

 package main
 import ("encoding/json"
 "net/http"
 "log")
func main() {
 http.HandleFunc("/", ExampleHandler)
 if err: = http.ListenAndServe("[127.0.0.1:8080](http://127.0.0.1:8080/)", nil);
 err != nil {
     panic(err)
 }
}
func ExampleHandler(w http.ResponseWriter, r * http.Request) {
 var ip string
 w.Header().Add("Content-Type", "application/json")
 forwarded: = r.Header.Get("X-FORWARDED-FOR")
 log.Print(forwarded)
 if forwarded != "" {
     log.Print("forwarded")
     ip = forwarded
 } else {
     log.Print("Not forwarded")
     ip = r.RemoteAddr
 }
 resp, _: = json.Marshal(map[string] string {
     "ip": ip,
 })
 w.Write(resp)
}

Hi Boris,

thanks for your answer.

Then If I set request.URL.Host it will overwrite the url I provide?

thanks and all the best!

Yes. The requests url is made up of different segments, a schema, possibly username and password, a host, a path, some query string parameters and a url fragment. The Host in the URL object is not the same as the Host on the request object, which is the one you want to change.

Hi Boris,

thanks for the clarification, now everything is more clear about this header options.

Then I just need to set req.Host but not req.URL.host this is great!

Just using req.Host it is working, but when the IP does not contain the page, I get the error

Error reading response. Get http://198.50.181.33: EOF

I guess this is what you mentioned before

Also, you should check if resp.Body is nil before calling Close on it

isn’t?

Thanks

Hey Boris,

I manage with your help to make that part of the code, work properly.

thank you very much :pray:

Happy to help :blush:

This topic was automatically closed 90 days after the last reply. New replies are no longer allowed.