~svn/ubuntu/oneiric/subversion/ppa

« back to all changes in this revision

Viewing changes to subversion/bindings/java/javahl/native/Inputer.cpp

  • Committer: Bazaar Package Importer
  • Author(s): Adam Conrad
  • Date: 2005-12-05 01:26:14 UTC
  • mfrom: (1.1.2 upstream)
  • Revision ID: james.westby@ubuntu.com-20051205012614-qom4xfypgtsqc2xq
Tags: 1.2.3dfsg1-3ubuntu1
Merge with the final Debian release of 1.2.3dfsg1-3, bringing in
fixes to the clean target, better documentation of the libdb4.3
upgrade and build fixes to work with swig1.3_1.3.27.

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
/**
 
2
 * @copyright
 
3
 * ====================================================================
 
4
 * Copyright (c) 2003-2004 CollabNet.  All rights reserved.
 
5
 *
 
6
 * This software is licensed as described in the file COPYING, which
 
7
 * you should have received as part of this distribution.  The terms
 
8
 * are also available at http://subversion.tigris.org/license-1.html.
 
9
 * If newer versions of this license are posted there, you may use a
 
10
 * newer version instead, at your option.
 
11
 *
 
12
 * This software consists of voluntary contributions made by many
 
13
 * individuals.  For exact contribution history, see the revision
 
14
 * history and logs, available at http://subversion.tigris.org/.
 
15
 * ====================================================================
 
16
 * @endcopyright
 
17
 *
 
18
 * @file Inputer.cpp
 
19
 * @brief Implementation of the class Inputer
 
20
 */
 
21
 
 
22
#include "Inputer.h"
 
23
#include "JNIUtil.h"
 
24
#include "JNIByteArray.h"
 
25
/**
 
26
 * create an Inputer object
 
27
 * @param jthis the java object to be stored
 
28
 */
 
29
Inputer::Inputer(jobject jthis)
 
30
{
 
31
    m_jthis = jthis;
 
32
}
 
33
/**
 
34
 * destroy an Inputer object
 
35
 */
 
36
Inputer::~Inputer()
 
37
{
 
38
    // the m_jthis does not need to be destroyed, because it is the passed
 
39
    // in parameter to the java method.
 
40
 
 
41
}
 
42
/**
 
43
 * create a svn_stream_t structure for this object. This will be used as an
 
44
 * input stream by subversion
 
45
 * @param pool  the pool, from which the structure is allocated
 
46
 * @return the input stream
 
47
 */
 
48
svn_stream_t *Inputer::getStream(const Pool & pool)
 
49
{
 
50
    // create a stream with this as the baton and set the read and close
 
51
    // functions
 
52
    svn_stream_t *ret = svn_stream_create(this, pool.pool());
 
53
    svn_stream_set_read(ret, Inputer::read);
 
54
    svn_stream_set_close(ret, Inputer::close);
 
55
    return ret;
 
56
}
 
57
/**
 
58
 * implements svn_read_fn_t to read to data into subversion
 
59
 * @param baton     an Inputer object for the callback
 
60
 * @param buffer    the buffer for the read data
 
61
 * @param len       on input the buffer len, on output the number of read bytes
 
62
 * @return a subversion error or SVN_NO_ERROR
 
63
 */
 
64
svn_error_t *Inputer::read(void *baton, char *buffer, apr_size_t *len)
 
65
{
 
66
    JNIEnv *env = JNIUtil::getEnv();
 
67
    // an object of our class is passed in as the baton
 
68
    Inputer *that = (Inputer*)baton;
 
69
 
 
70
    // the method id will not change during
 
71
    // the time this library is loaded, so
 
72
    // it can be cached.
 
73
    static jmethodID mid = 0;
 
74
    if(mid == 0)
 
75
    {
 
76
        jclass clazz = env->FindClass(JAVA_PACKAGE"/InputInterface");
 
77
        if(JNIUtil::isJavaExceptionThrown())
 
78
        {
 
79
            return SVN_NO_ERROR;
 
80
        }
 
81
        mid = env->GetMethodID(clazz, "read", "([B)I");
 
82
        if(JNIUtil::isJavaExceptionThrown() || mid == 0)
 
83
        {
 
84
            return SVN_NO_ERROR;
 
85
        }
 
86
        env->DeleteLocalRef(clazz);
 
87
        if(JNIUtil::isJavaExceptionThrown())
 
88
        {
 
89
            return SVN_NO_ERROR;
 
90
        }
 
91
    }
 
92
 
 
93
    // allocate a java byte array to read the data
 
94
    jbyteArray data =
 
95
        JNIUtil::makeJByteArray((const signed char*)buffer, *len);
 
96
    if(JNIUtil::isJavaExceptionThrown())
 
97
    {
 
98
        return SVN_NO_ERROR;
 
99
    }
 
100
 
 
101
    // read the data
 
102
    jint jread = env->CallIntMethod(that->m_jthis, mid, data);
 
103
    if(JNIUtil::isJavaExceptionThrown())
 
104
    {
 
105
        return SVN_NO_ERROR;
 
106
    }
 
107
 
 
108
    // put the java byte array into a helper object to retrieve the data bytes
 
109
    JNIByteArray outdata(data, true);
 
110
    if(JNIUtil::isJavaExceptionThrown())
 
111
    {
 
112
        return SVN_NO_ERROR;
 
113
    }
 
114
 
 
115
    // catch when the java method tells us, it read to much data.
 
116
    if(jread > *len)
 
117
        jread = -1;
 
118
 
 
119
    // in the case of success, copy the data back to the subversion buffer
 
120
    if(jread > 0)
 
121
        memcpy(buffer, outdata.getBytes(), jread);
 
122
 
 
123
    // copy the number of read bytes back to subversion
 
124
    *len = jread;
 
125
 
 
126
    return SVN_NO_ERROR;
 
127
}
 
128
/**
 
129
 * implements svn_close_fn_t to close the input stream
 
130
 * @param baton     an Inputer object for the callback
 
131
 * @return a subversion error or SVN_NO_ERROR
 
132
 */
 
133
svn_error_t *Inputer::close(void *baton)
 
134
{
 
135
    JNIEnv *env = JNIUtil::getEnv();
 
136
    // an object of our class is passed in as the baton
 
137
    Inputer *that = (Inputer*)baton;
 
138
 
 
139
    // the method id will not change during
 
140
    // the time this library is loaded, so
 
141
    // it can be cached.
 
142
    static jmethodID mid = 0;
 
143
    if(mid == 0)
 
144
    {
 
145
        jclass clazz = env->FindClass(JAVA_PACKAGE"/InputInterface");
 
146
        if(JNIUtil::isJavaExceptionThrown())
 
147
        {
 
148
            return SVN_NO_ERROR;
 
149
        }
 
150
        mid = env->GetMethodID(clazz, "close", "()V");
 
151
        if(JNIUtil::isJavaExceptionThrown() || mid == 0)
 
152
        {
 
153
            return SVN_NO_ERROR;
 
154
        }
 
155
        env->DeleteLocalRef(clazz);
 
156
        if(JNIUtil::isJavaExceptionThrown())
 
157
        {
 
158
            return SVN_NO_ERROR;
 
159
        }
 
160
    }
 
161
 
 
162
    // call the java object, to close the stream
 
163
    env->CallVoidMethod(that->m_jthis, mid);
 
164
    if(JNIUtil::isJavaExceptionThrown())
 
165
    {
 
166
        return SVN_NO_ERROR;
 
167
    }
 
168
 
 
169
    return SVN_NO_ERROR;
 
170
}