1/*
2 * Copyright 2012, The Android Open Source Project
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 *     http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16
17#ifndef A_NETWORK_SESSION_H_
18
19#define A_NETWORK_SESSION_H_
20
21#include <media/stagefright/foundation/ABase.h>
22#include <utils/KeyedVector.h>
23#include <utils/RefBase.h>
24#include <utils/Thread.h>
25
26#include <netinet/in.h>
27
28namespace android {
29
30struct AMessage;
31
32// Helper class to manage a number of live sockets (datagram and stream-based)
33// on a single thread. Clients are notified about activity through AMessages.
34struct ANetworkSession : public RefBase {
35    ANetworkSession();
36
37    status_t start();
38    status_t stop();
39
40    status_t createRTSPClient(
41            const char *host, unsigned port, const sp<AMessage> &notify,
42            int32_t *sessionID);
43
44    status_t createRTSPServer(
45            const struct in_addr &addr, unsigned port,
46            const sp<AMessage> &notify, int32_t *sessionID);
47
48    status_t createUDPSession(
49            unsigned localPort, const sp<AMessage> &notify, int32_t *sessionID);
50
51    status_t createUDPSession(
52            unsigned localPort,
53            const char *remoteHost,
54            unsigned remotePort,
55            const sp<AMessage> &notify,
56            int32_t *sessionID);
57
58    status_t connectUDPSession(
59            int32_t sessionID, const char *remoteHost, unsigned remotePort);
60
61    // passive
62    status_t createTCPDatagramSession(
63            const struct in_addr &addr, unsigned port,
64            const sp<AMessage> &notify, int32_t *sessionID);
65
66    // active
67    status_t createTCPDatagramSession(
68            unsigned localPort,
69            const char *remoteHost,
70            unsigned remotePort,
71            const sp<AMessage> &notify,
72            int32_t *sessionID);
73
74    status_t destroySession(int32_t sessionID);
75
76    status_t sendRequest(
77            int32_t sessionID, const void *data, ssize_t size = -1,
78            bool timeValid = false, int64_t timeUs = -1ll);
79
80    enum NotificationReason {
81        kWhatError,
82        kWhatConnected,
83        kWhatClientConnected,
84        kWhatData,
85        kWhatDatagram,
86        kWhatBinaryData,
87        kWhatNetworkStall,
88    };
89
90protected:
91    virtual ~ANetworkSession();
92
93private:
94    struct NetworkThread;
95    struct Session;
96
97    Mutex mLock;
98    sp<Thread> mThread;
99
100    int32_t mNextSessionID;
101
102    int mPipeFd[2];
103
104    KeyedVector<int32_t, sp<Session> > mSessions;
105
106    enum Mode {
107        kModeCreateUDPSession,
108        kModeCreateTCPDatagramSessionPassive,
109        kModeCreateTCPDatagramSessionActive,
110        kModeCreateRTSPServer,
111        kModeCreateRTSPClient,
112    };
113    status_t createClientOrServer(
114            Mode mode,
115            const struct in_addr *addr,
116            unsigned port,
117            const char *remoteHost,
118            unsigned remotePort,
119            const sp<AMessage> &notify,
120            int32_t *sessionID);
121
122    void threadLoop();
123    void interrupt();
124
125    static status_t MakeSocketNonBlocking(int s);
126
127    DISALLOW_EVIL_CONSTRUCTORS(ANetworkSession);
128};
129
130}  // namespace android
131
132#endif  // A_NETWORK_SESSION_H_
133