194ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla/* 294ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla * Copyright (C) 2014 The Android Open Source Project 394ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla * 494ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla * Licensed under the Apache License, Version 2.0 (the "License"); 594ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla * you may not use this file except in compliance with the License. 694ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla * You may obtain a copy of the License at 794ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla * 894ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla * http://www.apache.org/licenses/LICENSE-2.0 994ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla * 1094ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla * Unless required by applicable law or agreed to in writing, software 1194ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla * distributed under the License is distributed on an "AS IS" BASIS, 1294ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 1394ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla * See the License for the specific language governing permissions and 1494ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla * limitations under the License. 1594ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla */ 1694ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla 1794ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Sollapackage android.webkit; 1894ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla 19ee34ef1633592e31d4ea99c3a41492a82a970c11Bo Liuimport android.annotation.NonNull; 20ee34ef1633592e31d4ea99c3a41492a82a970c11Bo Liuimport android.annotation.Nullable; 21451e338c51e8c45efc0d21536dfae6f78f6d5e06Ignacio Sollaimport android.annotation.SystemApi; 2294ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Sollaimport android.app.ActivityThread; 2394ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Sollaimport android.app.Application; 2425f48886b2bc2f4edc65d80ff836561853b7ed50Adam Lesinskiimport android.app.ResourcesManager; 2594ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Sollaimport android.content.Context; 2625f48886b2bc2f4edc65d80ff836561853b7ed50Adam Lesinskiimport android.content.pm.ApplicationInfo; 2794ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Sollaimport android.content.res.Resources; 2894ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Sollaimport android.graphics.Canvas; 2994ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Sollaimport android.os.SystemProperties; 3094ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Sollaimport android.os.Trace; 3194ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Sollaimport android.util.SparseArray; 32f6829a0a618b4523619ec53c996b04d67e3186b9Chris Craikimport android.view.DisplayListCanvas; 3394ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Sollaimport android.view.View; 3494ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Sollaimport android.view.ViewRootImpl; 3594ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla 3625f48886b2bc2f4edc65d80ff836561853b7ed50Adam Lesinskiimport com.android.internal.util.ArrayUtils; 3725f48886b2bc2f4edc65d80ff836561853b7ed50Adam Lesinski 3894ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla/** 3994ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla * Delegate used by the WebView provider implementation to access 4094ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla * the required framework functionality needed to implement a {@link WebView}. 4194ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla * 4294ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla * @hide 4394ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla */ 44451e338c51e8c45efc0d21536dfae6f78f6d5e06Ignacio Solla@SystemApi 4594ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Sollapublic final class WebViewDelegate { 4694ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla 4794ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla /* package */ WebViewDelegate() { } 4894ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla 4994ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla /** 5094ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla * Listener that gets notified whenever tracing has been enabled/disabled. 5194ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla */ 5294ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla public interface OnTraceEnabledChangeListener { 5394ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla void onTraceEnabledChange(boolean enabled); 5494ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla } 5594ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla 5694ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla /** 5794ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla * Register a callback to be invoked when tracing for the WebView component has been 5894ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla * enabled/disabled. 5994ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla */ 6094ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla public void setOnTraceEnabledChangeListener(final OnTraceEnabledChangeListener listener) { 6194ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla SystemProperties.addChangeCallback(new Runnable() { 6294ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla @Override 6394ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla public void run() { 6494ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla listener.onTraceEnabledChange(isTraceTagEnabled()); 6594ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla } 6694ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla }); 6794ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla } 6894ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla 6994ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla /** 7094ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla * Returns true if the WebView trace tag is enabled and false otherwise. 7194ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla */ 7294ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla public boolean isTraceTagEnabled() { 7394ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla return Trace.isTagEnabled(Trace.TRACE_TAG_WEBVIEW); 7494ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla } 7594ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla 7694ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla /** 7794ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla * Returns true if the draw GL functor can be invoked (see {@link #invokeDrawGlFunctor}) 7894ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla * and false otherwise. 7994ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla */ 8094ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla public boolean canInvokeDrawGlFunctor(View containerView) { 81439266bbb533865405d5286fd944d79f7d49df0eBo Liu return true; 8294ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla } 8394ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla 8494ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla /** 8594ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla * Invokes the draw GL functor. If waitForCompletion is false the functor 8694ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla * may be invoked asynchronously. 8794ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla * 8894ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla * @param nativeDrawGLFunctor the pointer to the native functor that implements 8994ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla * system/core/include/utils/Functor.h 9094ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla */ 9194ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla public void invokeDrawGlFunctor(View containerView, long nativeDrawGLFunctor, 9294ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla boolean waitForCompletion) { 9344b49f070aafe8ad44efae87341121cce49ff11cJohn Reck ViewRootImpl.invokeFunctor(nativeDrawGLFunctor, waitForCompletion); 9494ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla } 9594ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla 9694ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla /** 9794ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla * Calls the function specified with the nativeDrawGLFunctor functor pointer. This 9894ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla * functionality is used by the WebView for calling into their renderer from the 9994ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla * framework display lists. 10094ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla * 10194ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla * @param canvas a hardware accelerated canvas (see {@link Canvas#isHardwareAccelerated()}) 10294ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla * @param nativeDrawGLFunctor the pointer to the native functor that implements 10394ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla * system/core/include/utils/Functor.h 10453f256948724b8d4009d8a8a47da96a06402f9a2Ignacio Solla * @throws IllegalArgumentException if the canvas is not hardware accelerated 10594ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla */ 10694ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla public void callDrawGlFunction(Canvas canvas, long nativeDrawGLFunctor) { 107f6829a0a618b4523619ec53c996b04d67e3186b9Chris Craik if (!(canvas instanceof DisplayListCanvas)) { 10894ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla // Canvas#isHardwareAccelerated() is only true for subclasses of HardwareCanvas. 10994ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla throw new IllegalArgumentException(canvas.getClass().getName() 110f6829a0a618b4523619ec53c996b04d67e3186b9Chris Craik + " is not a DisplayList canvas"); 11194ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla } 112e66471103abfc8b9142d895bac93dade67f558c3Bo Liu ((DisplayListCanvas) canvas).drawGLFunctor2(nativeDrawGLFunctor, null); 113e66471103abfc8b9142d895bac93dade67f558c3Bo Liu } 114e66471103abfc8b9142d895bac93dade67f558c3Bo Liu 115e66471103abfc8b9142d895bac93dade67f558c3Bo Liu /** 116e66471103abfc8b9142d895bac93dade67f558c3Bo Liu * Calls the function specified with the nativeDrawGLFunctor functor pointer. This 117e66471103abfc8b9142d895bac93dade67f558c3Bo Liu * functionality is used by the WebView for calling into their renderer from the 118e66471103abfc8b9142d895bac93dade67f558c3Bo Liu * framework display lists. 119e66471103abfc8b9142d895bac93dade67f558c3Bo Liu * 120e66471103abfc8b9142d895bac93dade67f558c3Bo Liu * @param canvas a hardware accelerated canvas (see {@link Canvas#isHardwareAccelerated()}) 121e66471103abfc8b9142d895bac93dade67f558c3Bo Liu * @param nativeDrawGLFunctor the pointer to the native functor that implements 122e66471103abfc8b9142d895bac93dade67f558c3Bo Liu * system/core/include/utils/Functor.h 123e66471103abfc8b9142d895bac93dade67f558c3Bo Liu * @param releasedRunnable Called when this nativeDrawGLFunctor is no longer referenced by this 124e66471103abfc8b9142d895bac93dade67f558c3Bo Liu * canvas, so is safe to be destroyed. 125e66471103abfc8b9142d895bac93dade67f558c3Bo Liu * @throws IllegalArgumentException if the canvas is not hardware accelerated 126e66471103abfc8b9142d895bac93dade67f558c3Bo Liu */ 127e66471103abfc8b9142d895bac93dade67f558c3Bo Liu public void callDrawGlFunction(@NonNull Canvas canvas, long nativeDrawGLFunctor, 128e66471103abfc8b9142d895bac93dade67f558c3Bo Liu @Nullable Runnable releasedRunnable) { 129e66471103abfc8b9142d895bac93dade67f558c3Bo Liu if (!(canvas instanceof DisplayListCanvas)) { 130e66471103abfc8b9142d895bac93dade67f558c3Bo Liu // Canvas#isHardwareAccelerated() is only true for subclasses of HardwareCanvas. 131e66471103abfc8b9142d895bac93dade67f558c3Bo Liu throw new IllegalArgumentException(canvas.getClass().getName() 132e66471103abfc8b9142d895bac93dade67f558c3Bo Liu + " is not a DisplayList canvas"); 133e66471103abfc8b9142d895bac93dade67f558c3Bo Liu } 134e66471103abfc8b9142d895bac93dade67f558c3Bo Liu ((DisplayListCanvas) canvas).drawGLFunctor2(nativeDrawGLFunctor, releasedRunnable); 13594ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla } 13694ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla 13794ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla /** 13894ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla * Detaches the draw GL functor. 13994ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla * 14094ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla * @param nativeDrawGLFunctor the pointer to the native functor that implements 14194ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla * system/core/include/utils/Functor.h 14294ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla */ 14394ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla public void detachDrawGlFunctor(View containerView, long nativeDrawGLFunctor) { 14494ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla ViewRootImpl viewRootImpl = containerView.getViewRootImpl(); 14594ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla if (nativeDrawGLFunctor != 0 && viewRootImpl != null) { 14694ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla viewRootImpl.detachFunctor(nativeDrawGLFunctor); 14794ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla } 14894ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla } 14994ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla 15094ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla /** 15194ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla * Returns the package id of the given {@code packageName}. 15294ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla */ 15394ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla public int getPackageId(Resources resources, String packageName) { 15494ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla SparseArray<String> packageIdentifiers = 15594ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla resources.getAssets().getAssignedPackageIdentifiers(); 15694ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla for (int i = 0; i < packageIdentifiers.size(); i++) { 15794ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla final String name = packageIdentifiers.valueAt(i); 15894ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla 15994ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla if (packageName.equals(name)) { 16094ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla return packageIdentifiers.keyAt(i); 16194ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla } 16294ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla } 16394ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla throw new RuntimeException("Package not found: " + packageName); 16494ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla } 16594ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla 16694ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla /** 16794ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla * Returns the application which is embedding the WebView. 16894ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla */ 16994ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla public Application getApplication() { 17094ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla return ActivityThread.currentApplication(); 17194ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla } 17294ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla 17394ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla /** 17494ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla * Returns the error string for the given {@code errorCode}. 17594ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla */ 17694ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla public String getErrorString(Context context, int errorCode) { 177f1a9b1bc249161fe1a9b0d85d4ed31153e4421c1Narayan Kamath return LegacyErrorStrings.getString(errorCode, context); 17894ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla } 17994ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla 18094ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla /** 181f6829a0a618b4523619ec53c996b04d67e3186b9Chris Craik * Adds the WebView asset path to {@link android.content.res.AssetManager}. 18294ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla */ 18394ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla public void addWebViewAssetPath(Context context) { 18425f48886b2bc2f4edc65d80ff836561853b7ed50Adam Lesinski final String newAssetPath = WebViewFactory.getLoadedPackageInfo().applicationInfo.sourceDir; 18525f48886b2bc2f4edc65d80ff836561853b7ed50Adam Lesinski 18625f48886b2bc2f4edc65d80ff836561853b7ed50Adam Lesinski final ApplicationInfo appInfo = context.getApplicationInfo(); 18725f48886b2bc2f4edc65d80ff836561853b7ed50Adam Lesinski final String[] libs = appInfo.sharedLibraryFiles; 18825f48886b2bc2f4edc65d80ff836561853b7ed50Adam Lesinski if (!ArrayUtils.contains(libs, newAssetPath)) { 18925f48886b2bc2f4edc65d80ff836561853b7ed50Adam Lesinski // Build the new library asset path list. 19025f48886b2bc2f4edc65d80ff836561853b7ed50Adam Lesinski final int newLibAssetsCount = 1 + (libs != null ? libs.length : 0); 19125f48886b2bc2f4edc65d80ff836561853b7ed50Adam Lesinski final String[] newLibAssets = new String[newLibAssetsCount]; 19225f48886b2bc2f4edc65d80ff836561853b7ed50Adam Lesinski if (libs != null) { 19325f48886b2bc2f4edc65d80ff836561853b7ed50Adam Lesinski System.arraycopy(libs, 0, newLibAssets, 0, libs.length); 19425f48886b2bc2f4edc65d80ff836561853b7ed50Adam Lesinski } 19525f48886b2bc2f4edc65d80ff836561853b7ed50Adam Lesinski newLibAssets[newLibAssetsCount - 1] = newAssetPath; 19625f48886b2bc2f4edc65d80ff836561853b7ed50Adam Lesinski 19725f48886b2bc2f4edc65d80ff836561853b7ed50Adam Lesinski // Update the ApplicationInfo object with the new list. 19825f48886b2bc2f4edc65d80ff836561853b7ed50Adam Lesinski // We know this will persist and future Resources created via ResourcesManager 19925f48886b2bc2f4edc65d80ff836561853b7ed50Adam Lesinski // will include the shared library because this ApplicationInfo comes from the 20025f48886b2bc2f4edc65d80ff836561853b7ed50Adam Lesinski // underlying LoadedApk in ContextImpl, which does not change during the life of the 20125f48886b2bc2f4edc65d80ff836561853b7ed50Adam Lesinski // application. 20225f48886b2bc2f4edc65d80ff836561853b7ed50Adam Lesinski appInfo.sharedLibraryFiles = newLibAssets; 20325f48886b2bc2f4edc65d80ff836561853b7ed50Adam Lesinski 20425f48886b2bc2f4edc65d80ff836561853b7ed50Adam Lesinski // Update existing Resources with the WebView library. 20525f48886b2bc2f4edc65d80ff836561853b7ed50Adam Lesinski ResourcesManager.getInstance().appendLibAssetForMainAssetPath( 20625f48886b2bc2f4edc65d80ff836561853b7ed50Adam Lesinski appInfo.getBaseResourcePath(), newAssetPath); 20725f48886b2bc2f4edc65d80ff836561853b7ed50Adam Lesinski } 20894ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla } 20994ef789f0cf0387df20c2c602857ada1e5abfdd6Ignacio Solla} 210