Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(393)

Side by Side Diff: media/capture/video/android/video_capture_device_android.cc

Issue 2186043002: VideoCaptureDeviceAndroid: add ThreadChecker, lock access to |client_|, mini cleanup (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: Created 4 years, 4 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « media/capture/video/android/video_capture_device_android.h ('k') | no next file » | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright (c) 2013 The Chromium Authors. All rights reserved. 1 // Copyright (c) 2013 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "media/capture/video/android/video_capture_device_android.h" 5 #include "media/capture/video/android/video_capture_device_android.h"
6 6
7 #include <stdint.h> 7 #include <stdint.h>
8 #include <utility> 8 #include <utility>
9 9
10 #include "base/android/jni_android.h" 10 #include "base/android/jni_android.h"
(...skipping 25 matching lines...) Expand all
36 // only used for USB model identifiers, so this implementation just indicates 36 // only used for USB model identifiers, so this implementation just indicates
37 // an unknown device model. 37 // an unknown device model.
38 return ""; 38 return "";
39 } 39 }
40 40
41 VideoCaptureDeviceAndroid::VideoCaptureDeviceAndroid(const Name& device_name) 41 VideoCaptureDeviceAndroid::VideoCaptureDeviceAndroid(const Name& device_name)
42 : state_(kIdle), got_first_frame_(false), device_name_(device_name) { 42 : state_(kIdle), got_first_frame_(false), device_name_(device_name) {
43 } 43 }
44 44
45 VideoCaptureDeviceAndroid::~VideoCaptureDeviceAndroid() { 45 VideoCaptureDeviceAndroid::~VideoCaptureDeviceAndroid() {
46 DCHECK(thread_checker_.CalledOnValidThread());
46 StopAndDeAllocate(); 47 StopAndDeAllocate();
47 } 48 }
48 49
49 bool VideoCaptureDeviceAndroid::Init() { 50 bool VideoCaptureDeviceAndroid::Init() {
50 int id; 51 int id;
51 if (!base::StringToInt(device_name_.id(), &id)) 52 if (!base::StringToInt(device_name_.id(), &id))
52 return false; 53 return false;
53 54
54 j_capture_.Reset(VideoCaptureDeviceFactoryAndroid::createVideoCaptureAndroid( 55 j_capture_.Reset(VideoCaptureDeviceFactoryAndroid::createVideoCaptureAndroid(
55 id, reinterpret_cast<intptr_t>(this))); 56 id, reinterpret_cast<intptr_t>(this)));
56 return true; 57 return true;
57 } 58 }
58 59
59 void VideoCaptureDeviceAndroid::AllocateAndStart( 60 void VideoCaptureDeviceAndroid::AllocateAndStart(
60 const VideoCaptureParams& params, 61 const VideoCaptureParams& params,
61 std::unique_ptr<Client> client) { 62 std::unique_ptr<Client> client) {
62 DVLOG(1) << __FUNCTION__; 63 DCHECK(thread_checker_.CalledOnValidThread());
63 { 64 {
64 base::AutoLock lock(lock_); 65 base::AutoLock lock(lock_);
65 if (state_ != kIdle) 66 if (state_ != kIdle)
66 return; 67 return;
67 client_ = std::move(client); 68 client_ = std::move(client);
68 got_first_frame_ = false; 69 got_first_frame_ = false;
69 } 70 }
70 71
71 JNIEnv* env = AttachCurrentThread(); 72 JNIEnv* env = AttachCurrentThread();
72 73
73 jboolean ret = Java_VideoCapture_allocate( 74 jboolean ret = Java_VideoCapture_allocate(
74 env, j_capture_.obj(), params.requested_format.frame_size.width(), 75 env, j_capture_.obj(), params.requested_format.frame_size.width(),
75 params.requested_format.frame_size.height(), 76 params.requested_format.frame_size.height(),
76 params.requested_format.frame_rate); 77 params.requested_format.frame_rate);
77 if (!ret) { 78 if (!ret) {
78 SetErrorState(FROM_HERE, "failed to allocate"); 79 SetErrorState(FROM_HERE, "failed to allocate");
79 return; 80 return;
80 } 81 }
81 82
82 // Store current width and height.
83 capture_format_.frame_size.SetSize( 83 capture_format_.frame_size.SetSize(
84 Java_VideoCapture_queryWidth(env, j_capture_.obj()), 84 Java_VideoCapture_queryWidth(env, j_capture_.obj()),
85 Java_VideoCapture_queryHeight(env, j_capture_.obj())); 85 Java_VideoCapture_queryHeight(env, j_capture_.obj()));
86 capture_format_.frame_rate = 86 capture_format_.frame_rate =
87 Java_VideoCapture_queryFrameRate(env, j_capture_.obj()); 87 Java_VideoCapture_queryFrameRate(env, j_capture_.obj());
88 capture_format_.pixel_format = GetColorspace(); 88 capture_format_.pixel_format = GetColorspace();
89 DCHECK_NE(capture_format_.pixel_format, media::PIXEL_FORMAT_UNKNOWN); 89 DCHECK_NE(capture_format_.pixel_format, media::PIXEL_FORMAT_UNKNOWN);
90 CHECK(capture_format_.frame_size.GetArea() > 0); 90 CHECK(capture_format_.frame_size.GetArea() > 0);
91 CHECK(!(capture_format_.frame_size.width() % 2)); 91 CHECK(!(capture_format_.frame_size.width() % 2));
92 CHECK(!(capture_format_.frame_size.height() % 2)); 92 CHECK(!(capture_format_.frame_size.height() % 2));
93 93
94 if (capture_format_.frame_rate > 0) { 94 if (capture_format_.frame_rate > 0) {
95 frame_interval_ = base::TimeDelta::FromMicroseconds( 95 frame_interval_ = base::TimeDelta::FromMicroseconds(
96 (base::Time::kMicrosecondsPerSecond + capture_format_.frame_rate - 1) / 96 (base::Time::kMicrosecondsPerSecond + capture_format_.frame_rate - 1) /
97 capture_format_.frame_rate); 97 capture_format_.frame_rate);
98 } 98 }
99 99
100 DVLOG(1) << "VideoCaptureDeviceAndroid::Allocate: queried frame_size=" 100 DVLOG(1) << __FUNCTION__ << " requested ("
101 << capture_format_.frame_size.ToString() 101 << capture_format_.frame_size.ToString() << ")@ "
102 << ", frame_rate=" << capture_format_.frame_rate; 102 << capture_format_.frame_rate << "fps";
103 103
104 ret = Java_VideoCapture_startCapture(env, j_capture_.obj()); 104 ret = Java_VideoCapture_startCapture(env, j_capture_.obj());
105 if (!ret) { 105 if (!ret) {
106 SetErrorState(FROM_HERE, "failed to start capture"); 106 SetErrorState(FROM_HERE, "failed to start capture");
107 return; 107 return;
108 } 108 }
109 109
110 { 110 {
111 base::AutoLock lock(lock_); 111 base::AutoLock lock(lock_);
112 state_ = kCapturing; 112 state_ = kCapturing;
113 } 113 }
114 } 114 }
115 115
116 void VideoCaptureDeviceAndroid::StopAndDeAllocate() { 116 void VideoCaptureDeviceAndroid::StopAndDeAllocate() {
117 DVLOG(1) << __FUNCTION__; 117 DCHECK(thread_checker_.CalledOnValidThread());
118 { 118 {
119 base::AutoLock lock(lock_); 119 base::AutoLock lock(lock_);
120 if (state_ != kCapturing && state_ != kError) 120 if (state_ != kCapturing && state_ != kError)
121 return; 121 return;
122 } 122 }
123 123
124 JNIEnv* env = AttachCurrentThread(); 124 JNIEnv* env = AttachCurrentThread();
125 125
126 jboolean ret = Java_VideoCapture_stopCapture(env, j_capture_.obj()); 126 const jboolean ret = Java_VideoCapture_stopCapture(env, j_capture_.obj());
127 if (!ret) { 127 if (!ret) {
128 SetErrorState(FROM_HERE, "failed to stop capture"); 128 SetErrorState(FROM_HERE, "failed to stop capture");
129 return; 129 return;
130 } 130 }
131 131
132 { 132 {
133 base::AutoLock lock(lock_); 133 base::AutoLock lock(lock_);
134 state_ = kIdle; 134 state_ = kIdle;
135 client_.reset(); 135 client_.reset();
136 } 136 }
137 137
138 Java_VideoCapture_deallocate(env, j_capture_.obj()); 138 Java_VideoCapture_deallocate(env, j_capture_.obj());
139 } 139 }
140 140
141 void VideoCaptureDeviceAndroid::TakePhoto(TakePhotoCallback callback) { 141 void VideoCaptureDeviceAndroid::TakePhoto(TakePhotoCallback callback) {
142 DVLOG(1) << __FUNCTION__; 142 DCHECK(thread_checker_.CalledOnValidThread());
143 { 143 {
144 base::AutoLock lock(lock_); 144 base::AutoLock lock(lock_);
145 if (state_ != kCapturing) 145 if (state_ != kCapturing)
146 return; 146 return;
147 } 147 }
148 148
149 JNIEnv* env = AttachCurrentThread(); 149 JNIEnv* env = AttachCurrentThread();
150 150
151 // Make copy on the heap so we can pass the pointer through JNI. 151 // Make copy on the heap so we can pass the pointer through JNI.
152 std::unique_ptr<TakePhotoCallback> heap_callback( 152 std::unique_ptr<TakePhotoCallback> heap_callback(
153 new TakePhotoCallback(std::move(callback))); 153 new TakePhotoCallback(std::move(callback)));
154 const intptr_t callback_id = reinterpret_cast<intptr_t>(heap_callback.get()); 154 const intptr_t callback_id = reinterpret_cast<intptr_t>(heap_callback.get());
155 if (!Java_VideoCapture_takePhoto(env, j_capture_.obj(), callback_id, 155 if (!Java_VideoCapture_takePhoto(env, j_capture_.obj(), callback_id,
156 next_photo_resolution_.width(), 156 next_photo_resolution_.width(),
157 next_photo_resolution_.height())) 157 next_photo_resolution_.height()))
158 return; 158 return;
159 159
160 { 160 {
161 base::AutoLock lock(photo_callbacks_lock_); 161 base::AutoLock lock(photo_callbacks_lock_);
162 photo_callbacks_.push_back(std::move(heap_callback)); 162 photo_callbacks_.push_back(std::move(heap_callback));
163 } 163 }
164 } 164 }
165 165
166 void VideoCaptureDeviceAndroid::GetPhotoCapabilities( 166 void VideoCaptureDeviceAndroid::GetPhotoCapabilities(
167 GetPhotoCapabilitiesCallback callback) { 167 GetPhotoCapabilitiesCallback callback) {
168 DCHECK(thread_checker_.CalledOnValidThread());
168 JNIEnv* env = AttachCurrentThread(); 169 JNIEnv* env = AttachCurrentThread();
169 170
170 PhotoCapabilities caps( 171 PhotoCapabilities caps(
171 Java_VideoCapture_getPhotoCapabilities(env, j_capture_.obj())); 172 Java_VideoCapture_getPhotoCapabilities(env, j_capture_.obj()));
172 173
173 // TODO(mcasas): Manual member copying sucks, consider adding typemapping from 174 // TODO(mcasas): Manual member copying sucks, consider adding typemapping from
174 // PhotoCapabilities to mojom::PhotoCapabilitiesPtr, https://crbug.com/622002. 175 // PhotoCapabilities to mojom::PhotoCapabilitiesPtr, https://crbug.com/622002.
175 mojom::PhotoCapabilitiesPtr photo_capabilities = 176 mojom::PhotoCapabilitiesPtr photo_capabilities =
176 mojom::PhotoCapabilities::New(); 177 mojom::PhotoCapabilities::New();
177 photo_capabilities->iso = mojom::Range::New(); 178 photo_capabilities->iso = mojom::Range::New();
(...skipping 14 matching lines...) Expand all
192 photo_capabilities->zoom->min = caps.getMinZoom(); 193 photo_capabilities->zoom->min = caps.getMinZoom();
193 photo_capabilities->focus_mode = caps.getAutoFocusInUse() 194 photo_capabilities->focus_mode = caps.getAutoFocusInUse()
194 ? mojom::FocusMode::AUTO 195 ? mojom::FocusMode::AUTO
195 : mojom::FocusMode::MANUAL; 196 : mojom::FocusMode::MANUAL;
196 callback.Run(std::move(photo_capabilities)); 197 callback.Run(std::move(photo_capabilities));
197 } 198 }
198 199
199 void VideoCaptureDeviceAndroid::SetPhotoOptions( 200 void VideoCaptureDeviceAndroid::SetPhotoOptions(
200 mojom::PhotoSettingsPtr settings, 201 mojom::PhotoSettingsPtr settings,
201 SetPhotoOptionsCallback callback) { 202 SetPhotoOptionsCallback callback) {
203 DCHECK(thread_checker_.CalledOnValidThread());
202 JNIEnv* env = AttachCurrentThread(); 204 JNIEnv* env = AttachCurrentThread();
203 // |width| and/or |height| are kept for the next TakePhoto()s. 205 // |width| and/or |height| are kept for the next TakePhoto()s.
204 if (settings->has_width || settings->has_height) 206 if (settings->has_width || settings->has_height)
205 next_photo_resolution_.SetSize(0, 0); 207 next_photo_resolution_.SetSize(0, 0);
206 if (settings->has_width) { 208 if (settings->has_width) {
207 next_photo_resolution_.set_width( 209 next_photo_resolution_.set_width(
208 base::saturated_cast<int>(settings->width)); 210 base::saturated_cast<int>(settings->width));
209 } 211 }
210 if (settings->has_height) { 212 if (settings->has_height) {
211 next_photo_resolution_.set_height( 213 next_photo_resolution_.set_height(
212 base::saturated_cast<int>(settings->height)); 214 base::saturated_cast<int>(settings->height));
213 } 215 }
214 216
215 if (settings->has_zoom) 217 if (settings->has_zoom)
216 Java_VideoCapture_setZoom(env, j_capture_.obj(), settings->zoom); 218 Java_VideoCapture_setZoom(env, j_capture_.obj(), settings->zoom);
217 callback.Run(true); 219 callback.Run(true);
218 } 220 }
219 221
220 void VideoCaptureDeviceAndroid::OnFrameAvailable( 222 void VideoCaptureDeviceAndroid::OnFrameAvailable(
221 JNIEnv* env, 223 JNIEnv* env,
222 const JavaParamRef<jobject>& obj, 224 const JavaParamRef<jobject>& obj,
223 const JavaParamRef<jbyteArray>& data, 225 const JavaParamRef<jbyteArray>& data,
224 jint length, 226 jint length,
225 jint rotation) { 227 jint rotation) {
226 DVLOG(3) << __FUNCTION__ << " length =" << length; 228 DVLOG(3) << __FUNCTION__ << " length =" << length;
227 229
228 base::AutoLock lock(lock_); 230 {
229 if (state_ != kCapturing || !client_.get()) 231 base::AutoLock lock(lock_);
230 return; 232 if (state_ != kCapturing || !client_.get())
233 return;
234 }
chfremer 2016/07/27 17:07:59 Not sure we really can reduce the scope of the loc
mcasas 2016/07/27 18:40:54 You're right, done.
231 235
232 jbyte* buffer = env->GetByteArrayElements(data, NULL); 236 jbyte* buffer = env->GetByteArrayElements(data, NULL);
233 if (!buffer) { 237 if (!buffer) {
234 LOG(ERROR) << "VideoCaptureDeviceAndroid::OnFrameAvailable: " 238 LOG(ERROR) << "VideoCaptureDeviceAndroid::OnFrameAvailable: "
235 "failed to GetByteArrayElements"; 239 "failed to GetByteArrayElements";
236 return; 240 return;
237 } 241 }
238 242
239 const base::TimeTicks current_time = base::TimeTicks::Now(); 243 const base::TimeTicks current_time = base::TimeTicks::Now();
240 if (!got_first_frame_) { 244 if (!got_first_frame_) {
(...skipping 127 matching lines...) Expand 10 before | Expand all | Expand 10 after
368 const tracked_objects::Location& from_here, 372 const tracked_objects::Location& from_here,
369 const std::string& reason) { 373 const std::string& reason) {
370 { 374 {
371 base::AutoLock lock(lock_); 375 base::AutoLock lock(lock_);
372 state_ = kError; 376 state_ = kError;
373 } 377 }
374 client_->OnError(from_here, reason); 378 client_->OnError(from_here, reason);
375 } 379 }
376 380
377 } // namespace media 381 } // namespace media
OLDNEW
« no previous file with comments | « media/capture/video/android/video_capture_device_android.h ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698