Present adds the certificate to the certificate cache and, if needed, starts a TLS server for answering TLS-ALPN challenges.
(ctx context.Context, chal acme.Challenge)
| 131 | // Present adds the certificate to the certificate cache and, if |
| 132 | // needed, starts a TLS server for answering TLS-ALPN challenges. |
| 133 | func (s *tlsALPNSolver) Present(ctx context.Context, chal acme.Challenge) error { |
| 134 | // we pre-generate the certificate for efficiency with multi-perspective |
| 135 | // validation, so it only has to be done once (at least, by this instance; |
| 136 | // distributed solving does not have that luxury, oh well) - update the |
| 137 | // challenge data in memory to be the generated certificate |
| 138 | cert, err := acmez.TLSALPN01ChallengeCert(chal) |
| 139 | if err != nil { |
| 140 | return err |
| 141 | } |
| 142 | |
| 143 | key := challengeKey(chal) |
| 144 | activeChallengesMu.Lock() |
| 145 | chalData := activeChallenges[key] |
| 146 | chalData.data = cert |
| 147 | activeChallenges[key] = chalData |
| 148 | activeChallengesMu.Unlock() |
| 149 | |
| 150 | // the rest of this function increments the |
| 151 | // challenge count for the solver at this |
| 152 | // listener address, and if necessary, starts |
| 153 | // a simple TLS server |
| 154 | |
| 155 | solversMu.Lock() |
| 156 | defer solversMu.Unlock() |
| 157 | |
| 158 | si := getSolverInfo(s.address) |
| 159 | si.count++ |
| 160 | if si.listener != nil { |
| 161 | return nil // already be served by us |
| 162 | } |
| 163 | |
| 164 | // notice the unusual error handling here; we |
| 165 | // only continue to start a challenge server if |
| 166 | // we got a listener; in all other cases return |
| 167 | ln, err := robustTryListen(s.address) |
| 168 | if ln == nil { |
| 169 | return err |
| 170 | } |
| 171 | |
| 172 | // we were able to bind the socket, so make it into a TLS |
| 173 | // listener, store it with the solverInfo, and start the |
| 174 | // challenge server |
| 175 | |
| 176 | si.listener = tls.NewListener(ln, s.config.TLSConfig()) |
| 177 | |
| 178 | go func() { |
| 179 | defer func() { |
| 180 | if err := recover(); err != nil { |
| 181 | buf := make([]byte, stackTraceBufferSize) |
| 182 | buf = buf[:runtime.Stack(buf, false)] |
| 183 | log.Printf("panic: tls-alpn solver server: %v\n%s", err, buf) |
| 184 | } |
| 185 | }() |
| 186 | defer close(si.done) |
| 187 | for { |
| 188 | conn, err := si.listener.Accept() |
| 189 | if err != nil { |
| 190 | if atomic.LoadInt32(&si.closed) == 1 { |
nothing calls this directly
no test coverage detected